对于聚合的功能MySQL是都是默默的发展。在最新的8.0.31版本中提供对集合操作INTERSECT和EXCEPT。这样一来,集合操作功能基本圆满了。MySQL5.7.40版本是不支持这个集合的。

In this release MySQL adds support for the SQL standard INTERSECT and EXCEPT table operators.
query_a INTERSECT query_b includes only rows appearing in both result sets.
query_a EXCEPT query_b returns any rows from the result set of query_a which are not in the result of query_b.
INTERSECT and EXCEPT both support DISTINCT and ALL, with DISTINCT the default in both cases. (This is the same as for UNION).
INTERSECT groups before EXCEPT or UNION, so TABLE r EXCEPT TABLE s INTERSECT TABLE t is evaluated as TABLE r EXCEPT (TABLE s INTERSECT TABLE t).
See INTERSECT Clause, and EXCEPT Clause, for additional information and examples. (Bug #1309, Bug #31336, Bug #11747209, Bug #11744757)

目前MySQL里提供的集合操作包含:【UNION ,UNION ALL,INTERSECT,EXCEPT】

集合类型 数据 结果
UNION ALL A={1,2,3},B={3,4,5,6} ALL={1,2,3,3,4,5,6}
UNION A={1,2,3},B={3,4,5,6} AUB={1,2,3,4,5,6}
INTERSECT A={1,2,3},B={3,4,5,6} A∩B={3}
EXCEPT A={1,2,3},B={3,4,5,6} A-B={1,2}

集合

测试集合

CREATE TABLE `DataSetA` (`id` bigint NOT NULL ,`name` varchar(10) DEFAULT NULL
);
INSERT INTO DataSetA(id,name) VALUES(1,'A'),(2,'A'),(3,'C');CREATE TABLE `DataSetB` (`id` bigint NOT NULL ,`name` varchar(10) DEFAULT NULL
);
INSERT INTO DataSetB(id,name) VALUES(3,'C'),(4,'D'),(5,'E'),(6,'F');CREATE TABLE `DataSetC` (`id` bigint NOT NULL, `name` varchar(10) DEFAULT NULL
);
INSERT INTO DataSetC(id,name) VALUES(6,'F'),(7,'G'),(7,'G'),(8,'H');

不同的结果操作集:

执行计划:

除了UNION ALL,都需要通过Using temporary 进行运算,所以性能还是存在一定影响。毕竟涉及临时表。

集合中的DISTINCT和ALL

INTERSECT和EXCEPT都支持DISTINCT和ALL与UNION相同),在这两种情况下默认为DISTINCT。
字面意义相同是否去重或全部显示。

uery_block INTERSECT [ALL | DISTINCT] query_block
mysql> table  DataSetC INTERSECT DISTINCT table DataSetC;
+----+------+
| id | name |
+----+------+
|  6 | F    |
|  7 | G    |
|  8 | H    |
+----+------+
3 rows in set (0.00 sec)mysql> table  DataSetC INTERSECT ALL table DataSetC;
+----+------+
| id | name |
+----+------+
|  6 | F    |
|  7 | G    |
|  7 | G    |
|  8 | H    |
+----+------+
4 rows in set (0.00 sec)
复制
备注:对于INTERSECT ALL,左手表中任何唯一行的最大支持的重复数是4294967295。

EXCEPT的问题ALL:无法去除所有匹配值

CREATE TABLE `DataSetD` (`id` bigint NOT NULL ,`name` varchar(10) DEFAULT NULL
);
INSERT INTO DataSetD(id,name) VALUES(1,'A'),(1,'A'),(1,'A'),(3,'C');mysql> SELECT * FROM DataSetD;
+----+------+
| id | name |
+----+------+
|  1 | A    |
|  1 | A    |
|  1 | A    |
|  3 | C    |
+----+------+
3 rows in set (0.00 sec)CREATE TABLE `DataSetE` (`id` bigint NOT NULL ,`name` varchar(10) DEFAULT NULL
);
INSERT INTO DataSetE(id,name) VALUES(1,'A');
mysql> SELECT * FROM DataSetE;
+----+------+
| id | name |
+----+------+
|  1 | A    |
+----+------+
1 row in set (0.00 sec)mysql > table  DataSetD EXCEPT ALL  table DataSetE;
+----+------+
| id | name |
+----+------+
|  1 | A    |
|  1 | A    |
|  3 | C    |
+----+------+
2 rows in set (0.00 sec)

备注:上诉中(1,A)信息,只有去掉一个,没有全部去掉。

注意事项

从底层实现和测试现象来看,集合对比方式是用object方式进行对比。只要列数量对就可以。类型无关紧要。但实际业务中肯定是满足字段,类型一致。

1.集合对比必须具有相同的列数,列数不同出现问题:

mysql> SELECT ID FROM DataSetA INTERSECT SELECT ID ,NAME FROM DataSetB;
ERROR 1222 (21000): The used SELECT statements have a different number of columns

2. 不同类型对比,可以进行对比。但对于最终结果来说就没意义。

mysql> SELECT ID FROM DataSetA  UNION  SELECT NAME FROM DataSetA;
+------+
| ID   |
+------+
| 1    |
| 2    |
| 3    |
| A    |
| C    |
+------+
5 rows in set (0.00 sec)

3.版本对比写法不同
MySQL 5.7相比,在MySQL 8.0中,对SELECT和集合的解析器规则进行了重构,使其更加一致并减少了重复.

  • LIMIT 写法
#mysql5.7.40不支持
mysql> (SELECT 1 AS result UNION SELECT 2) LIMIT 1;
ERROR 1064 (42000): You have an error in your SQL syntax;
check the manual that corresponds to your MySQL server version for the right
syntax to use near 'UNION SELECT 2) LIMIT 1' at line 1#mysql8.0.31支持
mysql> (SELECT 1 AS result UNION SELECT 2) LIMIT 1;
+--------+
| result |
+--------+
|      1 |
+--------+
1 row in set (0.00 sec)
  • FOR UPDATE 写法
#mysql5.7.40
mysql> SELECT 1 FOR UPDATE UNION SELECT 1 FOR UPDATE;
+---+
| 1 |
+---+
| 1 |
+---+
1 row in set (0.00 sec)mysql> (SELECT 1 FOR UPDATE) UNION (SELECT 1 FOR UPDATE);
+---+
| 1 |
+---+
| 1 |
+---+
1 row in set (0.00 sec)#mysql8.0.31 更严谨
mysql> SELECT 1 FOR UPDATE UNION SELECT 1 FOR UPDATE;
ERROR 1064 (42000): You have an error in your SQL syntax;
check the manual that corresponds to your MySQL server version for the right
syntax to use near 'UNION SELECT 1 FOR UPDATE' at line 1
mysql> (SELECT 1 FOR UPDATE) UNION (SELECT 1 FOR UPDATE);
+---+
| 1 |
+---+
| 1 |
+---+
1 row in set (0.00 sec)

总结

集合对比操作也算聚合的一种,在MySQL里性能影响还是比较可观的。基本要通过临时表进行处理。所以环境中需要合理使用。

参考:

https://dev.mysql.com/doc/relnotes/mysql/8.0/en/news-8-0-31.html

MySQL 8.0.31 集合操作INTERSECT和EXCEPT相关推荐

  1. MySQL 8.0新特性之INTERSECT和EXCEPT

    最近几年,MySQL 不断致力于兼容 SQL 标准.例如 MySQL 8.0 中的窗口函数.通用表表达式.检查约束等等. 最新发布的 MySQL 8.0.31 继续对 SQL 语句进行了增强,提供了缺 ...

  2. MySQL 8.0.31并行构建索引特性管窥

    测试效率提升36% ~ 100%,相当可观 本文目录 并行构建索引测试 进一步提高索引构建效率 并行构建索引的限制 MySQL 8.0.31于2022.10.11发布了,比我预计的日期早了一周,先赞一 ...

  3. MySQL 8.0.31 新增支持SQL标准中的交集(INTERSECT)和差集(EXCEPT)表操作符

    文章目录 概览 准备工作 交集( INTERSECT ) 差集( EXCEPT) 旧版本中交集.差集操作是如何实现的 总结 概览 最近的 MySQL 版本( 8.0.31 ) 中,新增了对 SQL 标 ...

  4. MySQL 8.0.31 最新版详细安装教程(下载+安装+配置+登录测试)

    名人说:君子生非异也,善假于物也.--荀子 Code_流苏(CSDN) o(‐^▽^‐)o很高兴你打开了这篇博客,跟着步骤一步步尝试安装吧.✧ 目录 一.下载MySQL 二.安装MySQL 三.配置M ...

  5. 写最好的Docker安装最新版MySQL8(mysql-8.0.31)教程(参考Docker Hub和MySQL官方文档)

    一.前言   MySQL官方安装包下载地址:   https://dev.mysql.com/downloads/mysql/     Docker Hub官方网址:   https://hub.do ...

  6. MySQL知识树 集合操作

    我们之前讲到了联接操作[对于联接操作的学习烦请移步:http://www.cnblogs.com/seker/p/6523592.html],联接操作可以看做是表之间的水平操作,通过联接操作得到的记录 ...

  7. mysql基础 Task04:集合运算

    1. 表的加减法 新建表 tbl_product2 ,供后面学习. create table tbl_product2 (product_id char(4) primary key,product_ ...

  8. CentOS 安装 mysql 8.0

    目录 下载 安装步骤 上传 解压安装 参考资料 补充报错解决 下载 MySQL :: Download MySQL Community Serverhttps://dev.mysql.com/down ...

  9. mysql高级之子查询,多表查询,外连接,集合操作,内部函数与数据控制_月隐学python第24课

    目录 ⼀.⾼级 1.1 ⼦查询 1.2 多表查询 1.3 外连接 1.4 集合操作 1.5 内部函数 ⼆.数据控制 2.1 事务 2.2 授权管理 ⼀.⾼级 1.1 ⼦查询 ⼦查询嵌⼊到其他查询语句中 ...

最新文章

  1. 计算机科学和Python编程导论(二 ) Python简介
  2. python入门作业编程题-Python语言编写有趣练习题!
  3. jQuery .attr() vs .prop()
  4. 用java制作扑克牌_阿里三面被挂,幸获内推,历经5轮终于拿到口碑offer(java研发)...
  5. R中千分位分隔符数值(美式数值)读取
  6. 搭建串口收发与存储双口RAM简易应用系统
  7. Arrays对数组,二分查找,冒泡排序
  8. 给入门级程序员的忠告
  9. C++ concurrent_queue::try_pop 方法
  10. 数组做函数参数的退化问题
  11. SIR传染病模型(微分方程系列1)
  12. 几种主流数据库类型简介
  13. 关于(backgroundImages -120 0 no-repeate)
  14. 【Linux】 浅谈 NCSI 及其在 Linux 上的实现
  15. Tomcat 服务器搭建
  16. 【Python+Selenium】输入关键词自动下载论文
  17. PLSQL代码调试Oracle dbms_utility返回错误
  18. 海思SDK学习(5)海思媒体处理软件平台MMP(4)VO视频输出
  19. 51nod-1278 相离的圆
  20. 数据分析 --- 如何分析数据

热门文章

  1. webRTC是怎么应对网络变化的
  2. ibaanalyzer使用教程_ibaPDA client软件快速设置方法资料.doc
  3. 利用python编写一段手柄控制程序
  4. 功率半导体芯片是什么_半导体功率器件可靠性水基清洗分析
  5. python 完成ATM取款机
  6. 线性模型|| 线性回归(Linear Regression)
  7. 服务器三大体系 SMP、NUMA、MPP 之详解
  8. php获取数据库表中总记录行数并打印
  9. html 实现二维效果图,25个很酷CSS3效果欣赏
  10. python实战游戏开发——添加飞船图像