我通过TableB将TableA与TableC建立多对多关系。也就是说,
TableA TableB TableC
id | val fkeyA | fkeyC id | data
我希望在TableA上做select sum(val)
,按照与TableC的关系进行分组。 TableA中的每个条目与TableC至少有一个关系。例如,
TableA
1 | 25
2 | 30
3 | 50
TableB
1 | 1
1 | 2
2 | 1
2 | 2
2 | 3
3 | 1
3 | 2
应输出
75
30
因为表中的第1行和第3行与TableC具有相同的关系,但TableA中的第2行与TableC具有不同的关系。
如何为此编写SQL查询?
答案 0 :(得分:1)
SELECT
sum(tableA.val) as sumVal,
tableC.data
FROM
tableA
inner join tableB ON tableA.id = tableB.fkeyA
INNER JOIN tableC ON tableB.fkeyC = tableC.id
GROUP by tableC.data
修改的 啊哈 - 我现在看到你得到了什么。让我再试一次:
SELECT
sum(val) as sumVal,
tableCGroup
FROM
(
SELECT
tableA.val,
(
SELECT cast(tableB.fkeyC as varchar) + ','
FROM tableB WHERE tableB.fKeyA = tableA.id
ORDER BY tableB.fkeyC
FOR XML PATH('')
) as tableCGroup
FROM
tableA
) tmp
GROUP BY
tableCGroup
答案 1 :(得分:1)
SELECT
SUM(val) AS sumVal
FROM
( SELECT
fkeyA
, GROUP_CONCAT(fkeyC ORDER BY fkeyC) AS grpC
FROM
TableB
GROUP BY
fkeyA
) AS g
JOIN
TableA a
ON a.id = g.fkeyA
GROUP BY
grpC
答案 2 :(得分:0)
SELECT sum(a.val)
FROM tablea a
INNER JOIN tableb b ON (b.fKeyA = a.id)
GROUP BY b.fKeyC
答案 3 :(得分:0)
似乎需要创建一个密钥列表才能允许分组:
75 -> key list = "1 2"
30 -> key list = "1 2 3"
因为T-SQL中不存在GROUP_CONCAT:
WITH CTE ( Id, key_list )
AS ( SELECT TableA.id, CAST( '' AS VARCHAR(8000) )
FROM TableA
GROUP BY TableA.id
UNION ALL
SELECT TableA.id, CAST( key_list + ' ' + str(TableB.id) AS VARCHAR(8000) )
FROM CTE c
INNER JOIN TableA A
ON c.Id = A.id
INNER join TableB B
ON B.Id = A.id
WHERE A.id > c.id --avoid infinite loop
)
Select
sum( val )
from
TableA inner join
CTE on (tableA.id = CTE.id)
group by
CTE.key_list