SQL Query查找不同表中两个字段之和的差异

时间:2018-06-05 09:08:10

标签: sql-server group-by aggregate-functions

我有3张表如下。我想找到平衡

Table A
studentID       Name
1               Bob
2               Sam
3              Sara

Table B
id  studentID   Credit
1   1       100
2   1       150
3   2       150
4   2       150
5   3       100
6   3       200

Table C
id  studentID   Amount      Type
1   1             50        cash
2   1            120        card
3   2            100        cash
4   2            130        card
5   3            50         card
6   3            150        card

我想得到如下结果表:Balance = Sum(credit) - sum(amount)其中type = card。

结果表

studentID       Name    Credit  Amount  Balance
1               Bob     250      120    130
2               Sam     300      130    170
3               Sara    300      200    100

EDIT
根据他的评论,这是他试过的查询

select A.studentID,
       A.Name,
       ISNULL(SUM(B.Credit),0) as [Credit], 
       ISNULL(SUM(C.Amount),0) as [Amount], 
       ISNULL(SUM(B.Credit),0) - (select ISNULL(SUM(C.Amount),0) from C Group by C.studentID having C.Type='card' and C.studentID=A.studentID) as [balance] 
from A 
  left outer join B on A.studentID = B.studentID 
  left outer join C on B.studentID = C.studentID 
group by A.studentID 

6 个答案:

答案 0 :(得分:2)

处理没有学分/金额的学生:

SELECT  A.STUDENTID, A.[NAME]
    , sum(B.CREDIT) AS [CREDIT]
    , sum(C.AMOUNT) AS [AMOUNT]
    , sum(B.CREDIT) - sum(C1.AMOUNT) AS [BALANCE]
FROM @TABLEA A
INNER JOIN (SELECT A.STUDENTID, isnull(SUM(B.CREDIT), 0) AS CREDIT FROM @TABLEA A LEFT JOIN @TABLEB B ON A.STUDENTID = B.STUDENTID GROUP BY A.STUDENTID) B ON A.STUDENTID = B.STUDENTID
INNER JOIN (SELECT A.STUDENTID, isnull(SUM(C.AMOUNT), 0) AS AMOUNT FROM @TABLEA A LEFT JOIN @TABLEC C ON A.STUDENTID = C.STUDENTID WHERE [TYPE] = 'CARD' GROUP BY A.STUDENTID) C ON B.STUDENTID = C.STUDENTID
INNER JOIN (SELECT A.STUDENTID, isnull(SUM(C.AMOUNT), 0) AS AMOUNT FROM @TABLEA A LEFT JOIN @TABLEC C ON A.STUDENTID = C.STUDENTID WHERE [TYPE] = 'CARD' GROUP BY A.STUDENTID) C1 ON B.STUDENTID = C1.STUDENTID
group by  A.STUDENTID, A.[NAME]

答案 1 :(得分:1)

这应该可以正常工作

SELECT
a.studentid,
a.Name,
sum(b.Credit) AS Credit,
ISNULL(c.Amount,0) AS Amount,
sum(b.Credit) - ISNULL(c.Amount,0) AS Balance
FROM  a
INNER JOIN  b ON a.studentid = b.StudentID
LEFT JOIN (select sum(amount) amount,studentid from c where type='card' 
group by studentid) as c ON a.studentid = c.studentid
GROUP BY a.studentid, a.Name,c.Amount

SQL Fiddle Link

答案 2 :(得分:0)

我还没有尝试过。请告诉我。

SELECT A.studentID,A.Name,B.Credit,C.Amount,(Credit-Balance) as Amount from A, B, C where A.studentID=B.studentID=C.studentID AND B.id=C.id AND C.type="card";

答案 3 :(得分:0)

这应该有效。它假设A中的所有学生都在B中。左连接符合以下事实:并非所有学生都有“卡”金额,如果不是,则返回0(否则,NULL减去的学分将返回NULL余额)。

   SELECT
    a.StudentID,
    a.Name,
    sum(b.Credit) AS Credit,
    ISNULL(sum(c.Amount),0) AS Amount,
    sum(b.Credit) - ISNULL(sum(c.Amount),0) AS Balance
    FROM tableA as a
    INNER JOIN tableB as b ON a.StudentID = b.StudentID
    LEFT JOIN tableC as c ON a.StudientID = c.StudentID AND c.[Type] = 'card'
    GROUP BY a.StudentID, a.Name

答案 4 :(得分:0)

这将是我的起点。确保正确的计算方法。 然后我开始重构。

 SELECT a.*, 
   (SELECT SUM(b.credit) FROM TableB b WHERE a.studentID = b.studentID) as Credit,
   (SELECT SUM(c.amount) FROM TableC c WHERE a.studentID = c.studentID) as Amount,
   ((SELECT SUM(b.credit) FROM TableB b WHERE a.studentID = b.studentID)
    - 
   (SELECT SUM(c.amount) FROM TableC c WHERE a.studentID = c.studentID)) as Balance
  FROM TableA a;

我制作了一个sqlFiddle:http://sqlfiddle.com/#!9/b86dc/7

答案 5 :(得分:0)

您可以尝试下面的查询

See live demo

select A.*, credit, amount, balance= coalesce(credit,0) - coalesce(amount,0) from
[table A] A
left join
(
select 
    studentid,
    credit= sum(credit)
from [table b] b 
group by studentid
)B
    on A.studentID= B.studentID
left join
(
select 
    studentid,
    amount= sum(amount)
from [table C] 
group by studentid
)C
on A.studentID=C.studentID