ERROR 1222报错源于UNION各SELECT子句列数不等,必须严格对齐数量、类型和顺序;修复需显式补列(如NULL或CAST)、统一字符集,并确保ORDER BY/LIMIT仅置于末尾。

ERROR 1222:The used SELECT statements have a different number of columns
这是 UNION 查询最常卡住的第一步——MySQL 直接报错,不给任何商量余地。它不是警告,是硬性拒绝执行,因为列数对不上就无法对齐行结构。你看到的错误信息里 ERROR 1222 (21000) 就是明确信号:两边 SELECT 子句返回的字段个数不等。
- 别数“表里有多少列”,要数你写的
SELECT里逗号分隔的表达式个数(*算一个,但展开后必须和另一边一致) -
SELECT id, name FROM t1是 2 列,SELECT id FROM t2是 1 列 → 必报错 - 用
SELECT *和显式列混搭极危险:t1 加了个新字段,SELECT * FROM t1突然变成 5 列,而另一边还是 4 列,上线就崩
用 NULL 或 '' 显式补列,但注意类型兼容
补列是最直接的修复方式,但不能随便填。MySQL 会尝试隐式转换,但失败时照样报错,比如把字符串字段和整数字段强行 union。
- 安全做法:用
NULL占位(它能适配多数类型),或用''(空字符串)补字符型字段 - 高风险操作:
SELECT id, name FROM t1 UNION SELECT id, 0 FROM t2—— 若name是VARCHAR,0 可能被转成'0',但若name允许NULL而 0 强制非空,后续逻辑可能出错 - 更稳妥写法:
SELECT id, name FROM t1 UNION SELECT id, CAST(NULL AS CHAR) FROM t2,显式声明类型意图
字符集或校对规则不一致也会触发“列数错误”假象
有时候你数了三遍列数都对得上,还是报 ERROR 1222。这很可能是字符集冲突导致 MySQL 在解析阶段就放弃匹配,误判为列结构不兼容。
- 典型场景:
t1.title是utf8mb4_general_ci,t2.title是utf8_general_ci,UNION 时 MySQL 报错 1271(illegal mix of collations),但在某些旧客户端或驱动里,错误可能被截断或误传为 1222 - 验证方法:单独执行每个
SELECT,看是否都能成功返回;再查字段定义:SHOW FULL COLUMNS FROM t1 LIKE 'title'; - 临时修复:在 SELECT 中强制统一,例如
CONVERT(title USING utf8mb4) COLLATE utf8mb4_unicode_ci AS title
ORDER BY 和 LIMIT 必须放在最后,否则语法解析失败
很多人想给每个子查询单独排序,比如 (SELECT ... ORDER BY id) UNION (SELECT ... ORDER BY id),结果 MySQL 报列数错——其实根本没到列数比对那步,语法就不合法。
- MySQL 不允许子查询带
ORDER BY(除非配合LIMIT且用括号包住),否则解析器会直接报错,错误提示可能误导为列数问题 - 正确位置:所有 UNION 完成后,只在末尾加一次
ORDER BY,例如:SELECT id,name FROM t1 UNION SELECT id,name FROM t2 ORDER BY id - 真需要控制各部分顺序?用
CASE WHEN生成排序权重列,再整体ORDER BY weight, id
实际写 UNION 时,列数只是表层门槛;真正容易翻车的是类型隐式转换、字符集隐性冲突、以及 ORDER BY 放错位置带来的连锁解析失败。检查时别只盯着数字,要进到每一列的数据定义和上下文环境里去看。


















