mysql中concat()遇null即返null,应使用ifnull()或coalesce()兜底;8.0+推荐concat_ws()自动跳过null;避免在where/order by中直接拼接以防索引失效,数字时间字段需显式转换。

MySQL里用CONCAT()拼接两个字段,但结果为NULL怎么办
只要任一参数为NULL,CONCAT()就直接返回NULL,不是空字符串。这是最常踩的坑。
常见错误现象:SELECT CONCAT(first_name, ' ', last_name) FROM users; 中某条记录first_name为空,整行显示NULL,而不是' John'或'Doe'。
- 用
IFNULL()或COALESCE()提前兜底:例如CONCAT(IFNULL(first_name, ''), ' ', IFNULL(last_name, '')) -
COALESCE()更通用,支持多个备选值,比如CONCAT(COALESCE(first_name, '', '未知'), ' ', COALESCE(last_name, '')) - 注意空格处理:如果两个字段都为空,结果会是
' '(一个空格),必要时加TRIM()
想用空格/逗号等分隔符拼接,但手动写太啰嗦
别重复写CONCAT(a, ' ', b, ' ', c)——MySQL 8.0+ 提供了更简洁的CONCAT_WS()(WS = With Separator)。
- 第一个参数是分隔符,后面所有非
NULL参数自动用它连接,NULL会被跳过 - 示例:
CONCAT_WS(', ', first_name, middle_name, last_name)→'Zhang, Li'(若middle_name为NULL) - 分隔符本身不能为
NULL,否则整个结果为NULL - 低版本MySQL(如5.7)不支持,只能老实用
CONCAT()配合IFNULL()
拼接后要参与排序或WHERE条件,性能很慢
在ORDER BY或WHERE里直接用CONCAT()会导致无法使用索引,尤其是大表。
- 避免:
WHERE CONCAT(name, '-', id) = 'Alice-123'—— 全表扫描 - 优先改写为可命中索引的形式,比如拆成
WHERE name = 'Alice' AND id = 123 - 真需要固定拼接值检索,考虑新增生成列(Generated Column)并建索引(MySQL 5.7+):
ALTER TABLE users ADD full_id VARCHAR(50) GENERATED ALWAYS AS (CONCAT(name, '-', id)) STORED;<br><pre class="brush:php;toolbar:false;">CREATE INDEX idx_full_id ON users(full_id);
字段类型是数字或时间,拼接时报错或格式难看
CONCAT()会隐式转类型,但行为不稳定:数字<code>0变空字符串,时间2023-01-01 10:30:00可能被截成'2023'。
- 显式转换更安全:
CONCAT(CAST(price AS CHAR), '元')或CONCAT(DATE_FORMAT(created_at, '%Y-%m-%d'), ' 上架') - 数字补零?用
LPAD(CAST(id AS CHAR), 6, '0'),比CONCAT('00000', id)可靠 - 避免依赖隐式转换,尤其在跨MySQL版本迁移时,行为可能变化
CONCAT()变成查询瓶颈或数据歧义源。











