【MySQL】性能优化之 index merge (1)
2023-09-14 08:57:29 时间
一 序言介绍
MySQL 5.0 版本之前,每条个表在查询时 只能使用一个索引,有些不知道此功能限制的开发总是在一个表上创建很多单独列的索引,以便当where条件中含有这些列是能够走上索引。但是这样并不是一个好方法,或者是“好心办坏事”,索引能够提供查询速度,但是也能给日常维护和IUD 操作带来维护成本。
MySQL 5.0 和之后的版本推出了一个新特性---索引合并优化(Index merge optimization),它让MySQL可以在查询中对一个表使用多个索引,对它们同时扫描,并且合并结果。
二 使用场景
Index merge算法有 3 种变体:例子给出最基本常见的方式:
2.1 对 OR 取并集
In this form, where the index has exactly N parts (that is, all index parts are covered):
1 key_part1=const1 AND key_part2=const2 ... AND key_partN=constN
2 Any range condition over a primary key of an InnoDB table.
3 A condition for which the Index Merge method intersection algorithm is applicable.
root@odbsyunying 02:34:41 explain select count(*) as cnt from `order` o WHERE o.order_status = 2 or o.buyer_id=1979459339672858 \G
*************************** 1. row ***************************
id: 1
select_type: SIMPLE
table: o
type: index_merge
possible_keys: buyer_id,order_status
key: order_status,buyer_id
key_len: 1,9
ref: NULL
rows: 8346
Extra: Using union(order_status,buyer_id); Using where
1 row in set (0.00 sec)
当 where 条件中 含有对两个索引列的 or 交集操作时 ,执行计划会采用 union merge 算法。
2.2 对 AND 取交集:
”In this form, where the index has exactly N parts (that is, all index parts are covered):
key_part1=const1 AND key_part2=const2 ... AND key_partN=constN
Any range condition over a primary key of an InnoDB table.“
root@odbsyunying 02:33:59 explain select count(*) as cnt from `order` o WHERE o.order_status = 2 and o.buyer_id=1979459339672858 \G
*************************** 1. row ***************************
id: 1
select_type: SIMPLE
table: o
type: index_merge
possible_keys: buyer_id,order_status
key: buyer_id,order_status
key_len: 9,1
ref: NULL
rows: 1
Extra: Using intersect(buyer_id,order_status); Using where; Using index
1 row in set (0.00 sec)
当where条件中含有索引列的and操作时,执行计划会采用intersect 并集操作。
2. 3 对 AND 和 OR 的组合取并集。
root@odbsyunying 02:42:19 explain select count(*) as cnt from `order` o WHERE o.order_status 2 or o.buyer_id=1979459339672858 \G
*************************** 1. row ***************************
id: 1
select_type: SIMPLE
table: o
type: index_merge
possible_keys: buyer_id,order_status
key: order_status,buyer_id
key_len: 1,9
ref: NULL
rows: 4585
Extra: Using sort_union(order_status,buyer_id); Using where
1 row in set (0.00 sec)
The difference between the sort-union algorithm and the union algorithm is that the sort-union algorithm must first fetch row IDs for all rows and sort them before returning any rows.
三 Index merge的 限制
MySQL在5.6.7之前,使用index merge有一个重要的前提条件:没有range可以使用。这个限制降低了MySQL index merge可以使用的场景。理想状态是同时评估成本后然后做出选择。因为这个限制,就有了下面这个已知的bad case :
SELECT * FROM t1 WHERE (goodkey1 10 OR goodkey2 20) AND badkey
优化器可以选择使用goodkey1和goodkey2做index merge,也可以使用badkey做range。因为上面的原则,无论goodkey1和goodkey2的选择度如何,MySQL都只会考虑range,而不会使用index merge的访问方式。这是一个悲剧...(5.6.7版本针对此有修复)
mysql index cond push down 索引下推 mysql 索引下推在8.0的代码中进行了重构,目前的逻辑比较清晰。本文对该代码进行相关的分析。本文介绍的代码为mysql-8.0.21版本。
[MySQL] 联合索引与using index condition [MySQL] 联合索引与using index condition1.测试联合索引的最左原则的时候, 发现了5.6版本后的新特性Index Condition Pushdown 2.含义就是存储引擎层根据索引尽可能的过滤数据,然后在返回给服务器层根据where其他条件进行过滤
MySQL Index Extensions Index Extensions含义 MySQL5.6开始 InnoDB可以通过主键自动扩展二级索引的功能称为Index Extensions,即二级索引除了存储本列索引的key值外,还存储着主键列key值。
MySQL · myrocks · clustered index特性 Cluster index介绍 最近在RDS MyRocks中,我们引入了一个重要功能,二级聚集索引(secondary clustering index). 我们知道innodb和rocksdb引擎的主键就是clustered index。
mysql index cond push down 索引下推 mysql 索引下推在8.0的代码中进行了重构,目前的逻辑比较清晰。本文对该代码进行相关的分析。本文介绍的代码为mysql-8.0.21版本。
[MySQL] 联合索引与using index condition [MySQL] 联合索引与using index condition1.测试联合索引的最左原则的时候, 发现了5.6版本后的新特性Index Condition Pushdown 2.含义就是存储引擎层根据索引尽可能的过滤数据,然后在返回给服务器层根据where其他条件进行过滤
MySQL Index Extensions Index Extensions含义 MySQL5.6开始 InnoDB可以通过主键自动扩展二级索引的功能称为Index Extensions,即二级索引除了存储本列索引的key值外,还存储着主键列key值。
MySQL · myrocks · clustered index特性 Cluster index介绍 最近在RDS MyRocks中,我们引入了一个重要功能,二级聚集索引(secondary clustering index). 我们知道innodb和rocksdb引擎的主键就是clustered index。
相关文章
- MySQL Error number: MY-010964; Symbol: ER_RPL_SLAVE_RESET_FILTER_OPTIONS; SQLSTATE: HY000 报错 故障修复 远程处理
- 优化MySQL性能:简单而有效的方法(如何提高mysql性能)
- MySQL连接码:主机地址简介(mysql的主机地址)
- 的优化优化MySQL文件夹的魔法(mysql文件夹)
- Mybatis操作MySQL存储过程实现数据库交互(mybatis调用mysql存储过程)
- Mysql: 开放端口保护数据安全(mysql开放端口)
- MySQL内存占用问题:如何优化解决(mysql内存占用过高)
- MySQL实现数据库拼串优化(mysql拼串)
- 开创MySQL性能新纪元:高性能MySQL第四版(高性能mysql第四版)
- MySQL备份权限:安全操作必修课(mysql备份权限)
- MySQL 配置文件的修改方法(mysql修改配置文件)
- 如何高效使用MySQL取数据技巧(mysql取数据)
- 深入理解MySQL联表操作,优化查询性能(mysql联表)
- 工具使用MySQL内置性能测试工具提升性能(mysql自带性能测试)
- MySQL优化实战指南:一次优化,持久性效果(mysql优化总结)
- 「MySQL读写分离软件」:提高数据库性能的不二之选(mysql读写分离软件)
- MySQL读写分离:带来性能和可用性的优势(mysql读写分离的好处)
- MySQL如何轻松导入大文件(mysql 导入 大文件)
- 如何在 MySQL 中临时修改参数(mysql中临时修改参数)
- MySQL中int数据类型的位数与使用方法(mysql中int位数)
- 如何解决MySQL中的Error 10055问题(mysql中10055)
- MySQL数据库从二进制存储到查询优化(binary mysql)
- 使用ARM板连接MySQL数据库(arm板连接mysql)
- AD域账户实现安全登录MySQL数据库(AD域账户登录mysql)
- MySQL教程如何使用两个字段去重(mysql两字段去重)
- MySQL数据库不支持使用中文命名表和字段名(mysql不能写中文名)
- MySQL连接串简化,无需配置了吗(mysql不用配连接串吗)
- 关于MySQL外键不建议使用,降低数据完整性和性能(25字)(mysql不推荐使用外键)