绝大多数关系数据库都通过一种称为 Null 特殊占位符支持 未知 或 不可知 的概念,Null 是缺失信息的占位符,本身不是值。Null 表示该位置没有值:Null 不是什么其他值,Null 不是真,也不是假,不是零,也不是空字符串。简单地理解,Null 就是自己:Null。可能一些人不明白其中的含义。掌握 SQLite 中的 Null,需要了解一些关键规则和观点。
- 第一:为了在逻辑表达式中使用 NULL,SQLite 使用所谓的三值(或三态)逻辑,Null 是真假值之一。下面的表格显示了逻辑与(And)和逻辑或(Or)与 Null 的关系。
X | Y | X AND Y | X OR Y |
---|---|---|---|
True | True | True | True |
True | False | False | True |
True | NULL | NULL | True |
False | False | False | False |
False | NULL | False | NULL |
NULL | NULL | NULL | NULL |
第二:可以通过
is null
或者is not null
操作符检测 NULL 是否存在。如果试图使用其他操作符,例如equal
、greater than
等。你可能会惊呆,看看第三条关于 NULL 的规则。第三:记住 NULL 不等于其他任何值,包括 NULL,不可以将 NULL 与其他值进行比较,NULL 绝对不会大于或小于其他任何 NULL。像下面这样粗心的语句常常不能返回任何行。
1 | select * from mtable where mvalue = null; |
NULL 不等于任何值,所以该 SQL 语句不会返回任何值。应该感到庆幸的是,SQLite 提供了一些与 NULL 相关的额外功能。其中第一个功能就是对 NULL 不等于任何值 这一限制进行变通。从 SQLite v3.6.19 开始,is 操作符可以让一个 null 等于另一个 null。最基本的形式是可以执行简单查询 SQL,看看 NULL 是否是 NULL。
1 | select NULL is NULL; |
非零的任何值都表示真。改例中,SQLite 告诉我们 NULL 等于 NULL。但是不要依赖这种行为。SQLite 的三态逻辑可能有些不适用,如果你期望在其他系统和编程语言中与 is 操作符一起工作的三态逻辑出现这样的预期结果,可能会遇到问题,这是公认的规则。
coalesce 函数作为 SQL99 标注的一部分,将一组值作为输入并返回其中第一个非 NULL。如下例所示:
1 | select coalesce(null, 7, null, 4); |
在本例中,coalesce 将返回第一个非 NULL 值 7。这在执行一些算数运算时是有帮助的,可以检测是否有 NULL 返回,如果有,可以返回更有意义的值(例如 0)来代替。
相反,nullif 函数输入两个参数,如果两个参数值相同,则返回 NULL;否则,返回第一个参数:
1 | select nullif(1, 1); |
注意: 如果使用 NULL,需要特别注意断言和聚合中引用可能存在的 NULL 值字段的查询,否则,NULL 可能在聚合中产生意想不到的效果。