sql优化之Explain sql

27 阅读4分钟

1.id 代表sql中查询语句的序列号,序列号越大则执行的优先级越高,序号一样谁在前谁先执行。id为null则最后执行。

2.select_type 查询类型,表示当前被分析的sql语句的查询的复杂度。这个字段有多个值。 ●SIMPLE:表示简单查询。 ●PRIMARY:表示复杂查询中的最外层的select查询语句 ●SUBQUERY:表是子查询语句 跟在select 关键字后面的select查询语句

3.table 表示当前访问的表的名称。 当from中有子查询时,table字段显示的是 N为derived的id的值。

4.partitions 返回的是数据分区的信息,不常用 这里不做分析。

5.type 这个字段决定mysql如何查找表中的数据,查找数据记录的大概范围。这个字段的所有值表示的从最优到最差依次为: system > const > eq_ref > ref > range > index > all; 一般来说我们优化到range就可以了 最好到ref。 null:type字段的值如果为null,那么表示当前的查询语句不需要访问表,只需要从索引树中就可以获取我们需要的数据; 一般如果是主键索引的话 ,查询主键字段或者唯一索引的话 查询主键字段 type字段的值就为null。 system/const:用户主键索引或者唯一索引查询时,只能匹配1条数据 一般可以对sql查询语句优化成一个常量,那么type一般就是system或者const,system是const的一个特例。 eq_ref:在进行连接查询时,例如left join 时,如果是使用主键索引或者唯一索引连接查询 ,结果返回一条数据,则type的值为一般为eq_ref。 ref: 相比较eq_ref,不使用主键索引或者唯一索引,使用的是普通索引或者唯一索引的部分前缀,索引与一个值进行比较后可能获取到多个符合条件的行,不在是唯一的行了。 range:通常使用范围查找,例如between,in,<,>,>=等使用索引进行范围检索。 index:扫描索引树就能获取到的数据,一般是扫描二级索引,并且不会从根节点扫描,一般直接扫描二级索引的叶子节点,速度比较慢。因为二级索引叶子节点不保存表中其他字段数据 只保存主键,所以二级索引还是比较小的,扫描速度相比All还是很快的。这里用到了覆盖索引,什么是覆盖索引:可以直接遍历索引树就能获取数据叫做覆盖索引。这里遍历name索引树就可以获取到主键id的值就是覆盖索引。 ALL:这是一种效率最低的type,需要扫描主键索引树的叶子节点,获取数据是表中其他列的数据,即全表扫描。 6.possible_keys 这个字段显示的是sql在查询时可能使用到的索引,但是不一定真的使用,只是一种可能。 如果在进行explain分析sql时,发现这一列有值,但是key列为null,因为mysql觉得可能会使用索引,但是又因为表中的数据很少,使用索引反而没有全表扫描效率高,那么mysql就不会使用索引查找,这种情况是可能发生的。 如果该列是NULL,则没有相关的索引。在这种情况下,可以通过检查 where 子句看是否可以创造一个适当的索引来提高查询性能,然后用 explain 查看效果。 7.key sql执行中真正用到的索引字段。 8.key_len 用到的索引字段的长度,通过这个字段可以显示具体使用到了索引字段中的哪些列(主要针对联合索引):计算公式如下 ● 字符串
char(n):n字节长度
varchar(n):如果是utf-8,则长度 3n + 2 字节,加的2字节用来存储字符串长度 ● 数值类型 tinyint:1字节
smallint:2字节
int:4字节
bigint:8字节 ● 时间类型 date:3字节
timestamp:4字节
datetime:8字节 如果字段允许为 NULL,需要1字节记录是否为 NULL 索引最大长度是768字节,当字符串过长时,mysql会做一个类似左前缀索引的处理,将前半部分的字符提取出来做索引。 9.ref 表示那些列或常量被用于查找索引列上的值 10.rows 表示在查询过程中检索了多少列 但是并不一定就是返回这么多列数据。 11.Extra(其他信息)