我遇到以下代码的问题:
SELECT PM.PM_Eng_Name, ISNULL(SUM(PMOutput.Quantity),0) AS TotalOut
FROM PM LEFT OUTER JOIN
PMOutput ON PM.PM_code = PMOutput.PM_code
WHERE (PMOutput.Output_Date BETWEEN ‘2013-01-01’ AND ‘2013-08-25’)
GROUP BY PM.PM_Eng_Name
当我运行此查询时,我只获得了在所选日期范围内具有输出事务的材料的总输出,而我需要生成所有PM_Eng_Names的总输出,其值为0在所选日期范围内没有输出交易 注意:当我删除WHERE子句时,我得到了完美的报告,但日期对我的项目很重要 有人可以帮我吗?
答案 0 :(得分:4)
要获得正确的结果,请将日期条件添加到join
而不是where
,并将isnull
添加到sum
内:
select
PM.PM_Eng_Name,
sum(isnull(PMOutput.Quantity, 0)) as TotalOut
from PM
left outer join PMOutput on PM.PM_code = PMOutput.PM_code and PMOutput.Output_Date BETWEEN ‘2013-01-01’ AND ‘2013-08-25’
group by PM.PM_Eng_Name
答案 1 :(得分:1)
我认为这是因为来自PMOutput
的'外部联接'列仅包含null,因此它们会被where子句过滤
会发生什么:
WHERE PMOutput.Output_Date is null or (PMOutput.Output_Date BETWEEN ‘2013-01-01’ AND ‘2013-08-25’)
答案 2 :(得分:0)
FROM
是初始逻辑查询阶段之一,在应用WHERE
之前完成。
在您的查询中应用WHERE
时,它会过滤掉大量行,因为它们的Output_Date为null
。
所以最初你的LEFT JOIN会这样做:
CREATE TABLE #j
(
Name char(8)
);
GO
INSERT INTO #j
values
('jim'),
('michael'),
('raj'),
('jason'),
('tim');
GO
CREATE TABLE #q
(
name char(8),
dateBirth datetime
);
GO
INSERT INTO #q
values
('jim', '01 jan 2010'),
('michael', '01 sep 2010');
GO
SELECT * 来自#j LEFT OUTER JOIN #q ON #j.Name =#q.Name;
返回以下内容:
SQL-server以不同的方式处理NULL
,具体取决于查询的哪个阶段找到空值以及哪个运算符应用于空值。在WHERE
cluse中,如果我们在此属性上指定过滤器,我们可以看到它丢弃具有null DateBirth的行:
SELECT *
FROM #j
LEFT OUTER JOIN #q ON
#j.Name = #q.Name
WHERE dateBirth BETWEEN '2000-01-01' AND '2020-01-01';
结果:
(“逻辑查询阶段”将是一个很好的Google)