在工作中呢我们常常会遇到慢sql需要优化的问题,这个时候通常我们需要用到explain来查看一个SQL语句的详细执行计划,以查看该SQL是否使用了索引,有没有进行全表扫描等,然后再根据执行计划,多当前SQL进行优化,或者为表的若干字段添加索引等。explain命令并不会真正执行当前SQL返回业务数据,而是返回当前SQL的执行计划。这里简单的介绍以下explain命令的执行结果和每个字段的意义。下面我们给出几个explain的示例。
explain
select min(score)
from exam_record
left join examination_info using(exam_id)
where tag = 'SQL' and score >=(
select avg(score)
from exam_record
left join examination_info using(exam_id)
where tag = 'SQL'
)
EXPLAIN
select
uid,
'activity1' as activity
from
exam_record
inner join examination_info using(exam_id)
where
year(start_time) = 2021
group by
uid
having
min(score) >= 85
union all
select
distinct uid,
'activity2' as activity
from
exam_record
inner join examination_info using(exam_id)
where
year(start_time) = 2021
and difficulty = 'hard'
and score >= 80
and timestampdiff(minute, start_time, submit_time) * 2 < duration
order by uid
explain的执行结果会返回十几个个字段,这个十二字段如上图所示,分别是:id、select_type、table、partitions、type、possible_keys、key、key_len、ref、rows、filtered和Extra。下面会依次介绍每个字段的详细意义。
id
id表示的是select查询语句的序号,代表了SQL语句执行的顺序,SQL按照id从大到小执行,id相同的为一组,从上到下执行。例如上图的SQL先执行子查询外部的查询语句,然后再执行子查询。
select_type
select_type表示查询的类型,也就是对应的是简单查询还是复杂查询,若是复杂查询则又包含简单的子查询、from子句的子查询、union查询等。下面就分别来看看select_type中的所有查询类型。
- SIMPLE: 简单的
select查询,未使用union或子查询等复杂查询。 - PRIMARY:复杂查询中的最外层的
select的类型就是PRIMARY。 - SUBQUERY:子查询中的
select语句的类型。 - DEPENDENT SUBQUERY:子查询中的第一个
select,依赖于外部查询。 - UNCACHEABLE SUBQUERY:一个子查询的结果不能被缓存,必须重新评估外链接的第一行。
- UNION:在
union语句中的第二个或后面的select语句的类型。 - UNION RESULT:UNION查询语句的结果
- DEPENDENT UNION:表示
union中的第二个或后面的select语句,取决于外面的查询。 - DERIVED:派生表的
select,from子句的子查询。
table
table表示查询数据来源与哪张表,若未使用别名,则为表名,若使用别名,则为别名。既可以表示已经存在表,又可以表示衍生表。
partitions
partitions表示的是分区信息,如果查询是基于分区表的话,会显示查询将访问的分区。
type
type表示访问类型或连接类型,即MySQL决定如何查找表中的行。type是MySQL查询优化中一个很重要的指标,访问性能从最优到最差分别为:system > const > eq_ref > ref > fulltext > ref_or_null > index_merge > unique_subquery > index_subquery > range > index > ALL,连接性能从最优到最差分别为:const > eq_ref > ref > range > index > ALL。
possible_keys
possible_keys指出如果MySQL能使用该索引在表中找到记录,查询涉及到的字段上若存在索引,则该索引将被列出,但不一定被查询使用。即该查询可以利用的索引,如果没有任何可利用的索引则显示为NULL。
key
key列显示MySQL实际在执行中会使用的索引,如果使用则必然包含在possible_keys中,因为possible_keys中列出了所有可能用于查出结果的索引信息。若实际执行中不使用索引,则为NULL。如果要想强制MySQL使用或忽视possible_keys中的索引,则需要在查询中使用force index、use index或者ignore index。
key_len
key_len表示索引中使用的字节数,查询中使用的索引的长度(最大可能长度),并非实际使用长度,理论上长度越短越好。
ref
ref表示列与索引的比较,表连接的匹配条件,表示哪些列或者常量被用于查询索引列上的值。
rows
rows表示估算的要扫描的行数,一般Mysql会根据统计表信息和索引的选用情况,估算出查找记录所要扫描的行数,注意这个并不是实际结果集的行数。
filtered
filtered表示当前查询返回的数据在server层过滤后,剩下多少满足查询的记录数量的比例,表示的是查询表行在表中的占比。
Extra
Extra表示的信息非常多,日后再说~~









网友评论