MyBatis-Plus中isNull与SQL语法详解:处理空值的正确姿势
MyBatis-Plus中isNull与SQL语法详解:处理空值的正确姿势
在使用MyBatis-Plus或直接操作SQL时,处理空值(NULL)和空字符串(“”)经常引发混淆和问题。本文将通过实战案例,详细分析为何
yard_location IS NULL
和yard_location = NULL
会返回不同结果,以及在 MyBatis-Plus 中如何正确使用isNull
方法来查询空值。
前言
在数据库中,NULL
表示没有值,这是一种特殊的标记。它与空字符串(“”)或数字 0 是不同的。在处理数据库查询时,正确区分和处理 NULL
值是非常重要的。
什么是 NULL?
NULL
表示数据库中没有值,是一种特殊的标记。它与空字符串(“”)或数字 0 是不同的。
如何查询 NULL?
查询字段是否为 NULL
应使用 IS NULL
或 IS NOT NULL
。例如:
SELECT * FROM dangerous_goods_log WHERE yard_location IS NULL;
而 yard_location = NULL
是无效的,任何值与 NULL
比较(如 =
、!=
)都返回 UNKNOWN
,即不匹配任何结果。
MyBatis-Plus 查询:为何 .eq("yard_location", "")
返回空数据?
在 MyBatis-Plus 中,.eq("yard_location", "")
生成的 SQL 类似于:
SELECT * FROM `dangerous_goods_log` WHERE yard_location = '';
这会查询 yard_location
为 空字符串 的记录,而不是 NULL
。如果数据库中 yard_location
为 NULL
而非 “”,此查询将不匹配任何结果。
如果使用 .isNull("yard_location")
,则生成的 SQL 为:
SELECT * FROM `dangerous_goods_log` WHERE yard_location IS NULL;
这是正确查询 NULL
的方式,因此返回正确结果。
MyBatis-Plus 中处理 NULL 的基本方法
MyBatis-Plus 提供了 isNull
和 isNotNull
方法,用于处理 NULL
值的查询条件。
查询字段值为 NULL 的数据
List<GoodsLogDO> goodsLogs = goodsLogMapper.selectList(
new QueryWrapper<GoodsLogDO>()
.isNull("yard_location") // 查询 yard_location 为 NULL 的记录
.in("dangerous_goods_status", 0L, 1L) // 状态为 0 或 1
);
生成的 SQL:
SELECT * FROM `dangerous_goods_log`
WHERE yard_location IS NULL
AND dangerous_goods_status IN (0, 1);
查询字段值非 NULL 的数据
List<GoodsLogDO> goodsLogs = goodsLogMapper.selectList(
new QueryWrapper<GoodsLogDO>()
.isNotNull("yard_location") // 查询 yard_location 非 NULL 的记录
.eq("dangerous_goods_status", 0L) // 状态为 0
);
生成的 SQL:
SELECT * FROM `dangerous_goods_log`
WHERE yard_location IS NOT NULL
AND dangerous_goods_status = 0;
查询字段为空字符串或 NULL 的记录
List<GoodsLogDO> goodsLogs = goodsLogMapper.selectList(
new QueryWrapper<GoodsLogDO>()
.and(wrapper -> wrapper
.isNull("yard_location") // yard_location 为 NULL
.or()
.eq("yard_location", "") // 或为空字符串
)
.eq("dangerous_goods_status", 1L); // 状态为 1
);
生成的 SQL:
SELECT * FROM `dangerous_goods_log`
WHERE (yard_location IS NULL OR yard_location = '')
AND dangerous_goods_status = 1;
总结
区分 NULL 和空字符串:在数据库中,
NULL
和 “” 是不同的。如果需要同时查询两种情况,必须显式使用IS NULL
和=
条件。MyBatis-Plus 默认行为:MyBatis-Plus 不会自动将空字符串(“”)视为
NULL
。SQL 默认比较规则:避免使用
= NULL
或!= NULL
,改用IS NULL
或IS NOT NULL
。空值赋值处理:插入数据时,如果字段需要为空,应显式插入
NULL
而非 “”,以确保查询逻辑一致。