explain 小结

个人学习笔记,谢绝转载!!!

原文:https://www.cnblogs.com/wshenjin/p/14774004.html


MySQL 的 explain 命令语句提供了 SQL 语句的执行和解析信息,explain 支持 select、delete、insert、replace 和 update 等语句,也支持对分区表的解析。通常 explain 用来获取 select 语句的执行计划,包括索引使用详情,表查询的顺序,表连接的方式等,并根据这些信息判断 select 执行效率,决定是否添加索引或改写 SQL 语句优化表连接方式以提高执行效率。

列名 说明
id 执行编号。表示查询中执行 select 子句或者操作表的顺序,id 的值越大,代表优先级越高,越先执行。id 大致会出现 3 种情况: 1、id 相同:具有同样的优先级,执行顺序由上而下,具体顺序由优化器决定; 2、id 不同:如果我们的 SQL 中存在子查询,那么 id 的序号会递增,id 值越大优先级越高,越先被执行 ; 3、以上两种同时存在:相同 id 划分为一组,这样就有三个组,同组的从上往下顺序执行,不同组 id 值越大,优先级越高,越先执行。
select_type 表示 select 查询的类型,主要是用于区分各种复杂的查询,例如:普通查询、联合查询、子查询等。
table 查询的表名,并不一定是真实存在的表,有别名显示别名,也可能为临时表。
partitions 查询时匹配到的分区信息,对于非分区表值为 NULL,当查询的是分区表时,partitions 显示分区表命中的分区情况。
type 数据访问 / 读取操作类型(ALL、index、range、ref、eq_ref、const/system、NULL)。
possible_keys 揭示哪一些索引可能有利于高效的查找,表示在 MySQL 中通过哪些索引,能让我们在表中找到想要的记录,一旦查询涉及到的某个字段上存在索引,则索引将被列出,但这个索引并不一定会是最终查询数据时所被用到的索引。
key 区别于 possible_keys,key 是查询中实际使用到的索引,若没有使用索引,显示为 NULL。
key_len 表示查询用到的索引长度(字节数),原则上长度越短越好 。
ref 显示了之前的表在 key 列记录的索引中查找值所用的列或常量。
rows 为了找到所需的行而需要读取的行数,估算值,不精确。通过把所有 rows 列值相乘,可粗略估算整个查询会检查的行数。这是评估 SQL 性能的一个比较重要的数据,mysql 需要扫描的行数,很直观的显示 SQL 性能的好坏,一般情况下 rows 值越小越好。
filtered 一个百分比的值,表里符合条件的记录数的百分比。这个字段表示存储引擎返回的数据在经过过滤后,剩下满足条件的记录数量的比例。
Extra 额外信息,如 using index、filesort 等。

type

重点字段 type 显示的是访问类型,是较为重要的一个指标,结果值从好到坏依次是:system > const > eq_ref > ref > fulltext > ref_or_null > index_merge > unique_subquery > index_subquery > range > index > ALL ,一般来说,得保证查询至少达到 range 级别,最好能达到 ref。

类型 说明
system 当表仅有一行记录时(系统表),数据量很少,往往不需要进行磁盘 IO,速度非常快。
const 表示查询时命中 primary key 主键或者 unique 唯一索引,或者被连接的部分是一个常量 (const) 值。这类扫描效率极高,返回数据量少,速度非常快。
eq_ref 查询时命中主键 primary key 或者 unique key 索引。
ref 使用非唯一性索引,会找到很多个符合条件的行。
ref_or_null 类似于 ref,区别在于 MySQL 会额外搜索包含 NULL 值的行。
index_merge 使用了索引合并优化方法,查询使用了两个以上的索引。
unique_subquery 子查询返回不重复的集合。
index_subquery 区别于 unique_subquery,用于非唯一索引,可以返回重复值。
range 使用索引选择行,仅检索给定范围内的行,即针对一个有索引的字段,给定范围检索数据。在 where 语句中使用 bettween...and、<、>、<=、in 等条件查询 type 都是 range。
index 索引遍历读取,即遍历全索引数据。
ALL 硬盘全表扫描,将遍历全表以找到匹配的行,性能最差。

select_type

表示 select 查询的类型,主要是用于区分各种复杂的查询,例如:普通查询、联合查询、子查询等。

查询的类型 说明
SIMPLE 表示最简单的 select 查询语句,也就是在查询中不包含子查询或者 union 交并差集等操作。
PRIMARY 当查询语句中包含任何复杂的子部分,最外层查询则被标记为 PRIMARY。
SUBQUERY 当 select 或 where 列表中包含了子查询,该子查询被标记为:SUBQUERY 。
DERIVED 表示包含在 from 子句中的子查询的 select,在我们的 from 列表中包含的子查询会被标记为 derived。
UNION 如果 union 后边又出现的 select 语句,则会被标记为 union;若 union 包含在 from 子句的子查询中,外层 select 将被标记为 derived。
UNION RESULT 代表从 union 的临时表中读取数据,而 table 列的 < union1,4 > 表示用第一个和第四个 select 的结果进行 union 操作。

extra

不适合在其他列中显示的信息,Explain 中的很多额外的信息会在 Extra 字段显示。

信息 说明
Using index 表示实现了覆盖索引,即查询的列被索引覆盖。【覆盖索引:一条 SQL 只需要通过索引就可以返回,我们所需要查询的数据(一个或几个字段),而不必通过二级索引,查到主键之后再通过主键查询整行数据(select * )。】
Using where 查询时未找到可用的索引,进而通过 where 条件过滤获取所需数据,但要注意的是并不是所有带 where 语句的查询都会显示 Using where 。【在查找使用索引的情况下,需要回表去查询所需的数据。】
Using index condition 查找使用了索引条件下推。
Using index;Using where 查找使用了索引,但是需要的数据都在索引列中能找到,所以不需要回表查询数据。
Using temporary 表示查询后结果需要使用临时表来存储,一般在排序或者分组查询时用到。
Using filesort 文件排序,表示无法利用索引完成的排序操作,也就是 ORDER BY 的字段没有索引,通常这样的 SQL 都是需要优化的。
Using join buffer 在我们联表查询的时候,如果表的连接条件没有用到索引,需要有一个连接缓冲区来存储中间结果。
Impossible where 表示在我们用不太正确的 where 语句,导致没有符合条件的行。
No tables used 查询语句中没有 FROM 子句,或者有 FROM DUAL 子句。

参考

https://mp.weixin.qq.com/s/hKYrjvVxA6PC10P3LSWMew

上一篇:jmeter for循环嵌套if学习2


下一篇:MySQL查询优化之explain的深入解析