EXPLAIN
- 名词:
QEP: Query Execution Plan,查询执行计划。
- 语法:
EXPLAIN [explain_type] {explainable_stmt }
explain_type:
{ EXTENDED | PARTITIONS | FORMAT = format_name}
format_name:
{ TRADITIONAL | JSON}
explainable_stmt:
{ SELECT statement | DELETE statement | INSERT statement | REPLACE statement | UPDATE statement }
通常EXPLAIN用于获取QEP,而DESCRIBE、DESC用于获取表结构信息。
explain_type中,EXTENDED和PARTITIONS 可不写,默认会输出这两列的信息。如:
mysql> EXPLAIN SELECT s1.key1, s2.key1 FROM s1 LEFT JOIN s2 ON s1.key1 = s2.key1 WHERE s2.common_field IS NOT NULL;
+----+-------------+-------+------------+------+---------------+----------+---------+-------------------+------+----------+-------------+
| id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | filtered | Extra |
+----+-------------+-------+------------+------+---------------+----------+---------+-------------------+------+----------+-------------+
| 1 | SIMPLE | s2 | NULL | ALL | idx_key1 | NULL | NULL | NULL | 9954 | 90.00 | Using where |
| 1 | SIMPLE | s1 | NULL | ref | idx_key1 | idx_key1 | 303 | xiaohaizi.s2.key1 | 1 | 100.00 | Using index |
+----+-------------+-------+------------+------+---------------+----------+---------+-------------------+------+----------+-------------+
2 rows in set, 1 warning (0.00 sec)
在我们使用EXPLAIN
语句查看了某个查询的执行计划后,紧接着还可以使用SHOW WARNINGS
语句查看与这个查询的执行计划有关的一些扩展信息,比如这样:
mysql> SHOW WARNINGS\G
*************************** 1. row ***************************
Level: Note
Code: 1003
Message: /* select#1 */ select `xiaohaizi`.`s1`.`key1` AS `key1`,`xiaohaizi`.`s2`.`key1` AS `key1` from `xiaohaizi`.`s1` join `xiaohaizi`.`s2` where ((`xiaohaizi`.`s1`.`key1` = `xiaohaizi`.`s2`.`key1`) and (`xiaohaizi`.`s2`.`common_field` is not null))
1 row in set (0.00 sec)
可以看到SHOW WARNINGS
展示出来的信息有三个字段,分别是Level
、Code
、Message
。我们最常见的就是Code
为1003
的信息,当Code
值为1003
时,Message
字段展示的信息类似于查询优化器将我们的查询语句重写后的语句。比如我们上边的查询本来是一个左(外)连接查询,但是有一个s2.common_field IS NOT NULL
的条件,着就会导致查询优化器把左(外)连接查询优化为内连接查询,从SHOW WARNINGS
的Message
字段也可以看出来,原本的LEFT JOIN
已经变成了JOIN
。
但是要注意,我们说Message
字段展示的信息类似于查询优化器将我们的查询语句重写后的语句,并不是等价于,也就是说Message
字段展示的信息并不是标准的查询语句,在很多情况下并不能直接拿到黑框框中运行,它只能作为帮助我们理解查MySQL
将如何执行查询语句的一个参考依据而已。
把EXPLAIN
语句输出的各个列的作用先大致罗列一下:
列名 | 描述 |
id |
在一个大的查询语句中每个SELECT 关键字都对应一个唯一的id |
select_type |
SELECT 关键字对应的那个查询的类型 |
table |
表名 |
partitions |
匹配的分区信息 |
type |
针对单表的访问方法 |
possible_keys |
可能用到的索引 |
key |
实际上使用的索引 |