LEFT JOIN在2表中

时间:2011-02-17 12:01:56

标签: sql sql-server tsql join aggregate-functions

为什么这个查询没有正确执行?

SELECT pr.ProjectNumber,
    SUM(ma.TotalAmount) As CostOfMaterials,
    SUM(ot.TotalAmount) AS CostOfOthers
FROM [dbo].[tblProject] AS pr
LEFT JOIN [dbo].[tblCostOfMaterials] AS ma ON pr.ProjectNumber=ma.ProjectNumber
LEFT JOIN [dbo].[tblCostOfOthers] AS ot ON pr.ProjectNumber=ot.ProjectNumber
GROUP BY pr.ProjectNumber

1 个答案:

答案 0 :(得分:1)

我认为您的意思是因为每个表都有多个特定项目编号的行,您可以多次计算相同的值。为避免这种情况,您可以使用

;WITH ma
     AS (select ProjectNumber,
                SUM(TotalAmount) as CostOfMaterials
         FROM   [dbo].[tblCostOfMaterials]
         GROUP  BY ProjectNumber),
     ot
     AS (select ProjectNumber,
                SUM(TotalAmount) as CostOfOthers
         FROM   [dbo].[tblCostOfOthers]
         GROUP  BY ProjectNumber)
SELECT pr.ProjectNumber, 
       CostOfMaterials, 
       CostOfOthers
FROM   [dbo].[tblProject] AS pr
       LEFT JOIN ma
         ON pr.ProjectNumber = ma.ProjectNumber
       LEFT JOIN ot
         ON pr.ProjectNumber = ot.ProjectNumber  

你得到这种行为的原因是因为你正在获得迷你笛卡尔联接

WITH tblProject (ProjectNumber) AS
(
SELECT 1
),tblCostOfMaterials(ProjectNumber, TotalAmount) AS
(
SELECT 1,101 UNION ALL
SELECT 1,201 UNION ALL
SELECT 1,301 
),
tblCostOfOthers(ProjectNumber, TotalAmount) AS
(
SELECT 1,100 UNION ALL
SELECT 1,200 
)
SELECT *
FROM [tblProject] AS pr
LEFT JOIN [tblCostOfMaterials] AS ma ON pr.ProjectNumber=ma.ProjectNumber
LEFT JOIN [tblCostOfOthers] AS ot ON pr.ProjectNumber=ot.ProjectNumber

返回

ProjectNumber ProjectNumber TotalAmount ProjectNumber TotalAmount
------------- ------------- ----------- ------------- -----------
1             1             101         1             100
1             1             101         1             200
1             1             201         1             100
1             1             201         1             200
1             1             301         1             100
1             1             301         1             200

您可以看到这些值与另一个表中匹配行的数量重复,因此SUM将不正确。