我理解null
代表缺失/未知值,因此null
不等于另一个null
,因为无法比较两个未知事物。例如
if null = null
select 'nulls are equal'
else
select 'nulls are not equal'
结果'nulls are not equal'
我在这里使用了=
代替is null
或is not null
来强调无法比较两个空值的事实。
来UNION
,UNION
应该消除重复值。我期望下面的代码返回两行null
,因为两个null
值不相等,但我在结果集中只得到一个空。
(select null as Col1)
union
(select null as Col1)
为什么SQL对'null作为未知值'的解释会在上述两个语句中发生变化?
答案 0 :(得分:4)
NULL无法比较,但SQL通常具有“IS DISTINCT FROM”的概念 SQL Server有一个Connect项目
1
来自NULL
= true 1 = null
是假的为了完整性,NULL
来自NULL
= false
我猜DISTINCT和UNION使用IS DISTINCT FROM
(如上面提到的Pரதீப்)
现在,SQL Server 确实在INTERSECT中有IS DISTINCT FROM
并且除外
DECLARE @t1 TABLE (t1col INT);
INSERT @t1 VALUES (1), (NULL), (2), (3), (3), (5), (5);
DECLARE @t2 TABLE (t2col INT);
INSERT @t2 VALUES (1), (NULL), (3), (4);
SELECT DISTINCT 't1 EXISTS t2', *
FROM @t1 t1 WHERE EXISTS (SELECT * FROM @t2 t2 WHERE t1.t1col = t2.t2col);
t1 EXISTS t2 1
t1 EXISTS t2 3
t1 EXISTS t2 3
SELECT DISTINCT 't1 INTERSECT t2', *
FROM @t1 INTERSECT SELECT 't1 INTERSECT t2', * FROM @t2;
t1 INTERSECT t2 NULL
t1 INTERSECT t2 1
t1 INTERSECT t2 3
INTERSECT和EXCEPT也会删除重复项,因为它们会进行半连接 EXISTS是反加入BTW
完整性
SELECT 't1 EXISTS t2', *
FROM @t1 t1 WHERE NOT EXISTS (SELECT * FROM @t2 t2 WHERE t1.t1col = t2.t2col);
t1 EXISTS t2 NULL
t1 EXISTS t2 2
t1 EXISTS t2 5
t1 EXISTS t2 5
SELECT 't1 EXCEPT t2', *
FROM @t1 EXCEPT SELECT 't1 EXCEPT t2', * FROM @t2;
t1 EXCEPT t2 2
t1 EXCEPT t2 5
从我的回答Why does EXCEPT exist in T-SQL?中添加了NULLs
的示例答案 1 :(得分:2)
UNION
基本上是SELECT DISTINCT
,因此它会消除重复的NULL值,但它与Equal操作不同。
使用UNION ALL
将为您提供所有记录,包括重复NULL。
至于你提问的第一部分。 NULL实际上等于NULL,但不是“=”。这会给你你期望的结果:
if null IS null
select 'nulls are equal'
else
select 'nulls are not equal'
处理空值时,This也很有帮助。
答案 2 :(得分:0)
尝试使用UNION ALL保留两个集合中的所有内容,而不删除重复项。