MySQL合并两表所有行并按日期排序的实现问题
解决两个表行合并(避免笛卡尔积)的正确SQL写法
你之前用JOIN导致笛卡尔积,是因为JOIN做的是行关联匹配,会把两个表的行两两组合,所以3×3得到9行。而你需要的是行堆叠合并(把两个表的行上下拼接),得用UNION ALL实现,具体步骤如下:
核心思路
- 用
UNION ALL替代JOIN:它会直接把两个结果集的行堆叠,不会产生笛卡尔积,且保留所有原始行(用UNION会自动去重,不需要的话用ALL更高效) - 对齐字段:两个表的字段必须数量、类型对应,对方表没有的字段用
NULL填充 - 统一排序逻辑:用
COALESCE(dateA, dateB)获取每行的有效日期,再做降序排序
具体SQL代码
基础版本(若两个表的id含义一致)
SELECT id, dateA, colA, NULL AS dateB, NULL AS colB FROM tableA UNION ALL SELECT id, NULL AS dateA, NULL AS colA, dateB, colB FROM tableB ORDER BY COALESCE(dateA, dateB) DESC;
优化版本(若两个表的id是各自主键,避免歧义)
如果tableA.id和tableB.id是各自表的独立主键,建议重命名区分:
SELECT id AS id_a, dateA, colA, NULL AS id_b, NULL AS dateB, NULL AS colB FROM tableA UNION ALL SELECT NULL AS id_a, NULL AS dateA, NULL AS colA, id AS id_b, dateB, colB FROM tableB ORDER BY COALESCE(dateA, dateB) DESC;
执行效果
- 结果集共6行(3行来自tableA,3行来自tableB)
- 所有字段都保留,缺失字段用
NULL填充 - 最终按日期(dateA或dateB)降序排列
内容的提问来源于stack exchange,提问作者Ondra
相关产品推荐
相关产品推荐

