今天我发现了一个奇怪的问题,即我有一个带有可空列的表,我尝试使用以下查询
SELECT * ID, MyNCol, 来自dbo。[MyTable] 在哪里MyNCol<> 'myvalue的'
并期望它返回Field MyNCol中没有'MyValue'值的所有行。但它没有在上面指定的列(MyNCol)中返回所有包含NULL的行。 所以我必须将我的查询重写为
SELECT * ID, MyNCol, 来自dbo。[MyTable] 在哪里MyNCol<> 'MyValue'或MyNCol IS NULL
现在我的问题是为什么第一个查询不足以执行我想要的东西。 :(
此致 Mubashar
答案 0 :(得分:1)
查看“ANSI NULLs”的行为。
标准地说,NULL!= NULL。您可以通过更改数据库上的ANSI NULLS enabled属性来更改此行为,但这会对列存储和查询执行产生很大影响。或者,您可以在SQL脚本中使用SET ANSI_NULLS语句。
SQL Server 2008的MSDN文档在此处:
SET ANSI_NULLS (Transact-SQL)
要特别注意比较的执行细节 - 即使设置ANSI_NULLS为OFF,列到列的比较也可能不符合您的预期。最佳做法是始终使用IS NULL和IS NOT NULL。
答案 1 :(得分:0)
不能对空值执行等式运算符。在SQL 2000中,您可以检查null = null,但是在2005年这已经改变了。
答案 2 :(得分:0)
NULL = UNKNOWN。所以你既不能说MyNCol ='我的价值',也不能说MyNCol<> '我的价值' - 都评估为UNKNOWN(就像'foo'+ MyNCol仍将变为NULL)。您发布的替代方法是:
WHERE COALESCE(MyNCol, 'Not my Value') <> 'My Value';
这将包括NULL列,因为比较变为false而不是unknown。我不喜欢这个选项,因为它在比较中依赖于一些神奇的值,即使只有当列为NULL时才会提供魔法值。