本篇文章给大家记录一次Mysql索引失效,分析一下Mysql索引失效原因,希望对大家有所帮助!
此文章包含Mysql的Where条件查询执行过程、范围查询使联合索引停止匹配、回表操作分析、常见索引失效场景、Extra分析等知识。【相关推荐:mysql视频教程】
6千万数据量的数据表出现了一个满查询,复现sql语句发现查询并没有走索引而是走全表查询,找出索引失效原因。
# sql语句 EXPLAIN SELECT count(*) FROM order_recipient_extend_tab WHERE start_date>'1628442000' and start_date<'1631120399' and station_id='1809' and status='2';
order_recipient_extend_tab 表有6千万数据,慢查询的查询字段包括 start_date、station_id、status,按照索引设计初衷会走但实际上失效的索引是:
联合索引 | 字段1 | 字段2 | 字段3 |
---|---|---|---|
idx_date_station_driver | start_date | station_id | driver_id |
了解Mysql怎么执行where条件查询,能更快速清晰地洞见索引失效的原因。此次慢查询中匹配度高的索引是idx_date_station_driver
,分析此次慢查询中where条件查询的执行过程。
Mysql对where条件提取规则主要可以归纳为三大类:Index Key (First Key & Last Key),Index Filter,Table Filter。
Index Key用于确定此次sql查询在索引树上的范围。一个范围包括起始和终止,Index First Key用于定位索引查询的起始范围,Index Last Key用于定位索引查询的终止范围。
Index First Key
提取规则:从索引的第一个字段开始,检查该字段在where条件中是否存在,若存在且条件是=、>=,则将对应的条件加入Index First Key之中,继续读取索引的下一个字段;若存在且条件是>,则将对应的条件加入Index First Key中,然后终止Index First Key的提取;若不存在,也终止Index First Key的提取。
Index Last Key
与Index First Key正好相反,提取规则:从索引的第一个字段开始,检查其在where条件中是否存在,若存在并且条件是=、bf8177cd8f553d3fc31606a276aecd12'1628442000',Index Last Key为: start_date64c438ffef82dc48be661242a1f021a5=、>、8703644d50d8e73a91bffaf4893e8797'1628442000',Index Last Key为: start_date15f4eaa2365aa4a7c3ea3e3960a6faba'1628442000' and start_dateb094f14c284d18154769bc7ffedce96a'1628442000' and start_timestamp_of_date822350b3bc3ac1b56d3209dbf6ec49b2),使用or操作。
字符串不加单引号索引失效。
like以通配符开头'%abc'。注意like ‘abc%’ 是可以走索引的。
order by 违反最左匹配原则,含非索引字段排序,会产生文件排序。
group by 违反最左匹配原则,含非索引字段分组,会导致产生临时表。
慢查询的分析离不开mysql的explain语句,explain主要关注两个字段Type和Extra。
Type表示访问数据的方式,Extra表示过滤和整理数据的方式。这里列举出来方便查找。
Type | Extra | ||
---|---|---|---|
ALL | 全表扫描 | Using index | 使用覆盖索引,不需要回表,不需要Mysql服务层过滤 |
index | 索引树全扫描 | Using where | 从存储引擎层获取数据,在Mysql服务层用where查询条件过滤数据。 |
range | 索引树范围扫描 | Using where; Using index | 索引范围扫描。索引扫描和全表扫描类似,只是发生的层面不一样。 |
ref | 非唯一性索引扫描,比如非唯一索引和唯一索引的非唯一前缀 | Using index condition | 使用索引下推,在存储引擎层充分利用查询索引字段过滤数据 |
eq_ref | 唯一性索引扫描,比如唯一索引、主键索引 | Using temporary | 临时表存储结果,用于排序和分组查询 |
const | 将查询转化成常量 | Using filesort | 文件排序,用于排序 |
NULL | 不用访问表或索引 | NULL | 回表 |
更多编程相关知识,请访问:编程入门!!
以上是Mysql索引失效怎么办?失效原因浅析的详细内容。更多信息请关注PHP中文网其他相关文章!