mysql中union关键字的实现示例

 更新时间:2026年02月04日 10:02:27   作者:哈里谢顿  
本文主要介绍了mysql中的union关键字详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧

MySQL 的 UNION 用于合并两个或多个 SELECT 语句的结果集,并自动去除重复行(相当于对结果集执行 DISTINCT)。

1. 基本语法与核心规则

SELECT column1, column2 FROM table1
UNION [ALL | DISTINCT]
SELECT column1, column2 FROM table2;

强制性规则

  • 列数必须相同:两个 SELECT 返回的列数必须一致
  • 数据类型兼容:对应位置的列类型不必完全相同,但必须可隐式转换(如 INT 和 DECIMAL)
  • 列名继承:结果集的列名取自第一个 SELECT 语句
  • ORDER BY 位置:只能放在最后一个 SELECT 之后,且排序依据必须是第一个 SELECT 的列名或别名

2. UNION vs UNION ALL

特性UNION (DISTINCT)UNION ALL
去重自动去重,行唯一保留所有行,包括重复
性能需要临时表+哈希排序去重,较慢直接追加结果,极快
使用场景必须确保唯一性时确定无重复或需要保留重复时

性能建议:除非业务需要去重,否则优先使用 UNION ALL。去重操作需要创建临时表、哈希比较和额外排序,大数据量时性能差距巨大。

3. 实际应用场景

场景 A:合并相似结构表(如分表)

-- 查询 2023 和 2024 年的订单(假设按年分表)
SELECT order_id, amount, created_at FROM orders_2023
UNION ALL
SELECT order_id, amount, created_at FROM orders_2024
ORDER BY created_at DESC
LIMIT 20;

场景 B:多维度统计报表

SELECT 'VIP用户' as user_type, COUNT(*) as cnt FROM users WHERE level >= 8
UNION ALL
SELECT '普通用户', COUNT(*) FROM users WHERE level BETWEEN 1 AND 7
UNION ALL
SELECT '访客', COUNT(*) FROM users WHERE level = 0;

场景 C:数据补全与兜底查询

-- 先查缓存表,若无结果再查主表(常见于配置表)
SELECT config_value FROM config_cache WHERE config_key = 'site_name'
UNION ALL
SELECT config_value FROM config WHERE config_key = 'site_name'
LIMIT 1;

4. 进阶用法

带排序和分页

(SELECT id, name FROM products WHERE category = 'A' ORDER BY price DESC LIMIT 10)
UNION ALL
(SELECT id, name FROM products WHERE category = 'B' ORDER BY price DESC LIMIT 10)
ORDER BY price DESC LIMIT 10;

注意:子查询中的 ORDER BY 必须配合 LIMIT 才生效,否则会被优化器忽略。

混合聚合与明细

SELECT city, sales_amount, NULL as detail FROM sales_summary
UNION ALL
SELECT city, amount, CONCAT(product_name, ':', quantity) FROM sales_detail;

5. 性能优化要点

  1. 索引利用:每个 SELECT 独立使用索引,UNION 本身不走索引
  2. 减少数据集:在子查询中先 WHERE 过滤,避免传递大量数据到 UNION 层
  3. 避免临时表写入UNION DISTINCT 会创建内存临时表(或磁盘临时表,若过大),可通过 SET tmp_table_size 调优
  4. 并行执行:MySQL 8.0.19+ 对非相关子查询的 UNION 可能启用并行查询

6. 常见陷阱

-- ❌ 错误:列数不匹配
SELECT id, name FROM t1
UNION
SELECT id FROM t2;  -- ERROR 1222

-- ❌ 错误:ORDER BY 位置错误
SELECT * FROM t1 ORDER BY id
UNION
SELECT * FROM t2;  -- ERROR 1221

-- ✅ 正确写法
SELECT * FROM t1
UNION
SELECT * FROM t2
ORDER BY id;  -- 使用第一个 SELECT 的列名排序

7. Django ORM 中的 UNION

如果你在使用 Django(看你之前关注过 Django 源码),可以这样使用:

from django.db.models import Q

# QuerySet.union() 默认使用 UNION ALL
qs1 = User.objects.filter(status='active').values('name', 'email')
qs2 = User.objects.filter(is_staff=True).values('name', 'email')

# UNION ALL
combined = qs1.union(qs2, all=True)

# UNION (去重)
combined_distinct = qs1.union(qs2)  # 或 all=False

注意:Django 的 union() 会强制转换为 SQL 的 UNION,且 QuerySet 被求值后返回的是列表而非 QuerySet,无法继续链式过滤。

总结UNION ALL 是合并结果集的高性能首选,UNION (DISTINCT) 仅在需要去重时使用。始终确保子查询列数一致,并在应用层处理复杂的排序逻辑。

到此这篇关于mysql中union关键字的实现示例的文章就介绍到这了,更多相关mysql union关键字内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • MySQL存储表情时报错:java.sql.SQLException: Incorrect string value:‘\xF0\x9F\x92\xA9\x0D\x0A...’的解决方法

    MySQL存储表情时报错:java.sql.SQLException: Incorrect string value:‘

    这篇文章主要给大家介绍了关于MySQL存储表情时报错:java.sql.SQLException: Incorrect string value: '\xF0\x9F\x92\xA9\x0D\x0A...'的解决方法,文中通过示例代码介绍的非常详细,需要的朋友可以参考借鉴,下面来一起看看吧。
    2018-04-04
  • Mysql-Insert插入过慢的原因记录和解决方案

    Mysql-Insert插入过慢的原因记录和解决方案

    这篇文章主要介绍了Mysql-Insert插入过慢的原因记录和解决方案,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2023-08-08
  • MySQL的Replace into 与Insert into on duplicate key update真正的不同之处

    MySQL的Replace into 与Insert into on duplicate key update真正的不同

    今天听同事介绍oracle到mysql的数据migration,他用了Insert into ..... on duplicate key update ...,我当时就想怎么不用Replace呢,于是回来就仔细查了下,它们果然还是有区别的
    2014-02-02
  • MySQL窗口函数的具体使用

    MySQL窗口函数的具体使用

    本文主要介绍了MySQL窗口函数的具体使用,文中通过示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2021-11-11
  • Mysql 查询数据库容量大小的方法步骤

    Mysql 查询数据库容量大小的方法步骤

    这篇文章主要介绍了Mysql 查询数据库容量大小的方法步骤,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2020-06-06
  • MySQL使用pt-table-sync修复主从数据一致性问题

    MySQL使用pt-table-sync修复主从数据一致性问题

    在 MySQL 主从架构中,数据一致性是运维的核心诉求,大事务中断、误操作等都可能导致主从数据偏差,今天分享一款 Percona Toolkit 旗下的神器pt-table-sync,通过实战案例教大家高效修复主从数据不一致问题,需要的朋友可以参考下
    2026-04-04
  • MySQL主从同步、读写分离配置步骤

    MySQL主从同步、读写分离配置步骤

    根据要求配置MySQL主从备份、读写分离,结合网上的文档,对搭建的步骤和出现的问题以及解决的过程做了如下笔记
    2012-03-03
  • 从0到1学会MySQL单表查询

    从0到1学会MySQL单表查询

    这篇文章主要给大家介绍了关于如何从0到1学会MySQL单表查询的相关资料,单表查询是指从一张表数据中查询所需的数据,文中通过代码介绍的非常详细,需要的朋友可以参考下
    2023-11-11
  • infobright导入数据遇到特殊字符报错的解决方法

    infobright导入数据遇到特殊字符报错的解决方法

    这篇文章主要介绍了infobright导入数据遇到特殊字符报错的解决方法,Infobright是开源的MySQL数据仓库解决方案,需要的朋友可以参考下
    2014-07-07
  • MySQL事务隔离级别和一致性详解

    MySQL事务隔离级别和一致性详解

    文章讲解了数据库事务的隔离性及四个级别(读未提交、读提交、可重复读、串行化),不同级别解决不同并发问题,强调一致性需用户与数据库共同保障
    2025-08-08

最新评论