开题概述
explain,数据库提供的一种查看SQL执行计划,并不实际执行SQL的关键字。不同的数据库使用该关键字后查询的结果并不一样,本文以MySQL为案例进行讲解
案例
语法:explain sql语句(增删改查SQL都可以)
常用于查询SQL的性能排查,在添加explain关键字后执行的结果如下图,示例SQL:
explain
select p.id,count(*) from danran_test_user_log l
inner join (select * from danran_test_user p where p.id > 1 and id < 2000) p on l.product_id = p.id
group by p.id;
从上图可以看出:查询danran_test_user表数据检索可使率(结果的行数占需读取行数的百分比)很高,关于该表的查询优化顺序可以放到最后;danran_test_user_log表数据检索可使率较低而且是全表扫描,说明该表查询可能需要优化;
主题
我是如何得出以上结论的呢?
主要是查看explain返回的结果,接下来我们再看看具体每列的含义是什么?首先,我们看下MySQL的官方文档:
这里简单按照个人理解翻译下常用几个列
id
表示SQL执行顺序,id相同时从上往下顺序执行,id不同时值越大优先级别越高。
select_type
我们看下MySQL官网的说明 这里简单按照个人理解翻译下常用几个:
- SIMPLE: 简单查询,不包含子查询和union这样的复杂查询,很常见的类型
- PRIMARY:包含子查询SQL的主查询,表示最外层,很常见的类型
- SUBQUERY:子查询
- UNION**:union语句里的SQL元素,union查询。
table
表名称,如果表有别名,则展示表别名
partitions
分区名称
type
查询时候的连接方式,下面按照从好到差顺序依次介绍:
- null:无须使用索引,即可查到数据,如:
explain select 1;
- system:该表只有一行(=系统表)。这是const联接类型的特例 。
- const:该表最多具有一个匹配行,该行在查询开始时读取。因为只有一行,所以优化器的其余部分可以将这一行中列的值视为常量。 const表非常快,因为它们只能读取一次。常见案例就是根据主键查询数据了
- eq_ref:一个表的主键或唯一索引与另一个表唯一索引或主键关联查询时会返回该类型。除了 system和 const类型,这是最好的联接类型。
- ref:一个表与另一个表关联查询时会返回该类型。很常见的类型
- fulltext:使用FULLTEXT 索引执行联接。MySQL5.6及之后Innodb也支持全文索引了,但是目前还存在BUG(已踩坑),不推荐使用哈
- range:在给定的范围内检索数据,很常见的类型
- ALL:全表扫描,尽量避免此种情况
possible_keys
可能使用的索引名称
key
实际选择的索引。这里虽说是实际执行的索引,explain执行计划可能与实际执行并不相同,取决于数据情况,MySQL优化器会根据具体数据情况选择最终执行计划
key_len
所选键的长度
ref
该ref列显示将哪些列或常量与该key列中命名的索引进行比较,以 从表中选择行。
rows
该rows列表示MySQL认为执行查询必须检查的行数。对于InnoDB表,此数字是估计值,可能并不总是准确的。
filtered
该filtered列表示按表条件过滤的表行的估计百分比。最大值为100,这表示未过滤行。值从100减小表示过滤量增加。 rows显示了检查的估计行数,rows× filtered显示了与下表连接的行数。例如,如果 rows为1000且 filtered为50.00(50%),则与下表连接的行数为1000×50%= 500。
Extra
此列包含有关MySQL如何解析查询的其他信息。有关不同值的说明,这里就不具体概述了,详情可以查看官方文档