MySQL 中 IS NULL
是唯一可靠的空值判断方式
MySQL 的
NULL不是值,而是“缺失值”的标记,因此不能用
= NULL或
!= NULL判断——这些表达式永远返回
NULL(即逻辑假),查不到任何结果。必须用
IS NULL和
IS NOT NULL。
常见错误现象:
SELECT * FROM user WHERE name = NULL返回空结果集,即使表里真有
name为
NULL的记录。
WHERE col = NULL→ 永远不匹配,等价于
WHERE NULL
WHERE col IS NULL→ 正确匹配该列为
NULL的行
WHERE col NULL→ 这是 MySQL 特有的“安全等于”,可替代
IS NULL,但语义稍隐晦,不推荐初学者依赖
区分 NULL
、空字符串 ''
和数值 0
三者在 MySQL 中完全独立:一个字段可以是
NULL(未赋值)、
''(明确赋了空字符串)、或
0(数值零)。查询时必须分开处理。
例如用户注册表中
phone字段:
IS NULL→ 用户没填手机号(字段值为空)
= ''→ 用户填了但提交的是空字符串(可能是前端校验漏掉)
IS NULL OR phone = ''→ 合并两种“无效手机号”场景
注意:
LENGTH(phone) = 0无法捕获
NULL,因为
LENGTH(NULL)返回
NULL,需配合
IS NULL使用。
IS NULL
在索引和性能上的实际影响
如果字段有普通 B+Tree 索引(如
INDEX(name)),
WHERE name IS NULL可以走索引——前提是该索引允许
NULL(InnoDB 默认允许)。但要注意: 联合索引中,只有最左前缀包含
IS NULL字段且其左侧全为等值条件时,才可能命中索引
ORDER BY ... DESC配合
IS NULL时,
NULL默认排在最前(升序)或最后(降序),行为可被
ORDER BY col IS NULL, col显式控制 使用
IFNULL()或
COALESCE()包裹字段后判断(如
IFNULL(name, '') = '')会强制索引失效
批量更新或删除时如何安全处理 NULL
写
UPDATE或
DELETE语句时,
IS NULL的逻辑必须显式写出,不能靠默认值或隐式转换。
示例:把所有未填邮箱的用户状态设为待验证
UPDATE user SET status = 'pending' WHERE email IS NULL;
容易踩的坑:
WHERE email = ''不会更新
NULL行,哪怕业务上认为“没填”和“填了空串”等价
SET email = NULL和
SET email = ''效果完全不同,前者清空字段值为
NULL,后者设为空字符串 如果字段定义为
NOT NULL DEFAULT '',插入时省略该字段会自动填
'',而非
NULL,此时
IS NULL永远查不到它
真正要小心的,是字段定义本身是否允许
NULL,以及应用层插入数据时到底传了什么——数据库只认你写进去的字面量,不猜意图。
