MySQL使用UNION合并两表数据时按批次号正确排序的实现方法
问题原因
当前SQL返回结果不符合预期,核心有三点:
- 排序方向错误:需求为升序排列,原SQL写了
ORDER BY batch_no DESC,会按倒序返回结果 - 排序规则不匹配:UNION最终返回的列混合了纯数字、带
-的拼接字符串,直接排序时MySQL会按字符串逐字符比较ASCII值,例如字符串'10'会排在'2'之前,完全不符合数值排序逻辑 - 缺少子批次排序维度:同一主批次下的多个子批次没有独立的数值排序键,无法保证
7-1排在7-2、7-3之前
解决方案
给两个UNION分支统一增加数值类型的排序辅助列,先按主批次号数值升序,再按子批次号数值升序,最终仅返回需要展示的批次字段即可,辅助列不需要对外展示。
参考SQL:
SELECT batch_display FROM ( -- 无子批次分支:子批次排序值设为0,和另一分支的列数、字段类型对齐 SELECT CAST(batch_no AS CHAR) AS batch_display, batch_no AS main_sort, 0 AS sub_sort FROM batch UNION ALL -- 有子批次分支:拼接展示值,保留数值类型的主、子批次号作为排序依据 SELECT CONCAT(batch_no, '-', subbatch_no) AS batch_display, batch_no AS main_sort, subbatch_no AS sub_sort FROM subbatch ) t -- 按数值维度排序,完全匹配预期顺序 ORDER BY main_sort ASC, sub_sort ASC;
这里用
UNION ALL替代UNION,因为两张表的输出结果不存在重复值,可省去去重操作的性能开销,执行效率更高。
执行后返回结果顺序为:1、2、3、4、5、6、7-1、7-2、7-3、8-1、8-2、9、10、11-1、11-2、12,完全符合需求。
内容的提问来源于stack exchange,提问作者Palendrone
相关产品推荐
相关产品推荐

