当前位置:首页 > Mysql教程 > 列表

msyql中Explain的用法详解

发布:smiling 来源: PHP粉丝网  添加日期:2014-10-10 10:41:33 浏览: 评论:0 

ref可以用于使用=或<=>操作符的带索引的列,在下面的例子中,MySQL可以使用ref联接来处理ref_tables,代码如下:

  1. SELECT * FROM ref_table WHERE key_column=expr; 
  2.  
  3. SELECT * FROM ref_table,other_table 
  4.   WHERE ref_table.key_column=other_table.column
  5.  
  6. SELECT * FROM ref_table,other_table 
  7.   WHERE ref_table.key_column_part1=other_table.column 
  8.     AND ref_table.key_column_part2=1; 
  9.  
  10. --例如: 
  11.  
  12. mysql> drop index idx_t3_id on t3; 
  13. Query OK, 1000 rows affected (0.03 sec) 
  14. Records: 1000  Duplicates: 0  Warnings: 0 
  15.  
  16. mysql> create index idx_t3_id on t3(id) ; 
  17. Query OK, 1000 rows affected (0.04 sec) 
  18. Records: 1000  Duplicates: 0  Warnings: 0 
  19.  
  20. mysql> explain select * from t3,t4 where t3.id=t4.accountid; 
  21. +----+-------------+-------+------+-------------------+-----------+---------+----------------------+------+-------+ 
  22. | id | select_type | table | type | possible_keys     | key       | key_len | ref                  | rows | Extra | 
  23. +----+-------------+-------+------+-------------------+-----------+---------+----------------------+------+-------+ 
  24. |  1 | SIMPLE      | t4    | ALL  | NULL              | NULL      | NULL    | NULL                 | 1000 |       | 
  25. |  1 | SIMPLE      | t3    | ref  | PRIMARY,idx_t3_id | idx_t3_id | 4       | dbatest.t4.accountid |    1 |       | 
  26. +----+-------------+-------+------+-------------------+-----------+---------+----------------------+------+-------+ 
  27. rows in set (0.00 sec) 

(5).ref_or_null

该联接类型如同ref,但是添加了MySQL可以专门搜索包含NULL值的行,在解决子查询中经常使用该联接类型的优化,在下面的例子中,MySQL可以使用ref_or_null联接来处理ref_tables,代码如下:

SELECT * FROM ref_table WHERE key_column=expr OR key_column IS NULL;

(6).index_merge

该联接类型表示使用了索引合并优化方法,在这种情况下,key列包含了使用的索引的清单,key_len包含了使用的索引的最长的关键元素,代码如下:

  1. mysql> explain select * from t4 where id=3952602 or accountid=31754306 ; 
  2. +----+-------------+-------+-------------+----------------------------+----------------------------+---------+------+------+------------------------------------------------------+ 
  3. | id | select_type | table | type        | possible_keys              | key                        | key_len | ref  | rows | Extra                                                | 
  4. +----+-------------+-------+-------------+----------------------------+----------------------------+---------+------+------+------------------------------------------------------+ 
  5. |  1 | SIMPLE      | t4    | index_merge | idx_t4_id,idx_t4_accountid | idx_t4_id,idx_t4_accountid | 4,4     | NULL |    2 | Using union(idx_t4_id,idx_t4_accountid); Using where | 
  6. +----+-------------+-------+-------------+----------------------------+----------------------------+---------+------+------+------------------------------------------------------+ 
  7. 1 row in set (0.00 sec) 

(7).unique_subquery

该类型替换了下面形式的IN子查询的ref:

value IN (SELECT primary_key FROM single_table WHERE some_expr)

unique_subquery是一个索引查找函数,可以完全替换子查询,效率更高.

(8).index_subquery

该联接类型类似于unique_subquery,可以替换IN子查询,但只适合下列形式的子查询中的非唯一索引:

value IN (SELECT key_column FROM single_table WHERE some_expr)

(9).range

只检索给定范围的行,使用一个索引来选择行,key列显示使用了哪个索引。key_len包含所使用索引的最长关键元素,在该类型中ref列为NULL.

当使用=、<>、>、>=、<、<=、IS NULL、<=>、BETWEEN或者IN操作符,用常量比较关键字列时,可以使用range,代码如下:

  1. mysql> explain select * from t3 where id=3952602 or id=3952603 ; 
  2. +----+-------------+-------+-------+-------------------+-----------+---------+------+------+-------------+ 
  3. | id | select_type | table | type  | possible_keys     | key       | key_len | ref  | rows | Extra       | 
  4. +----+-------------+-------+-------+-------------------+-----------+---------+------+------+-------------+ 
  5. |  1 | SIMPLE      | t3    | range | PRIMARY,idx_t3_id | idx_t3_id | 4       | NULL |    2 | Using where | 
  6. +----+-------------+-------+-------+-------------------+-----------+---------+------+------+-------------+ 
  7. 1 row in set (0.02 sec) 

Explain 列的解释:

table 显示这一行的数据是关于哪张表的.

type 这是重要的列,显示连接使用了何种类型,从最好到最差的连接类型为const、eq_reg、ref、range、indexhe和ALL.

possible_keys 显示可能应用在这张表中的索引。如果为空,没有可能的索引。可以为相关的域从WHERE语句中选择一个合适的语句

key 实际使用的索引。如果为NULL,则没有使用索引。很少的情况下,MYSQL会选择优化不足的索引。这种情况下,可以在SELECT语句中使用USE INDEX(indexname)来强制使用一个索引或者用IGNORE INDEX(indexname)来强制MYSQL忽略索引

key_len 使用的索引的长度。在不损失精确性的情况下,长度越短越好

ref 显示索引的哪一列被使用了,如果可能的话,是一个常数

rows MYSQL认为必须检查的用来返回请求数据的行数

Extra 关于MYSQL如何解析查询的额外信息。这里可以看到的坏的例子是Using    temporary和Using filesort,意思MYSQL根本不能使用索引,结果是检索会很慢

Extra 列返回的描述的意义

Distinct 一旦MYSQL找到了与行相联合匹配的行,就不再搜索了

Not exists MYSQL优化了LEFT JOIN,一旦它找到了匹配LEFT JOIN标准的行,就不再搜索了

Range checked for each

Record(index map:#)没有找到理想的索引,因此对于从前面表中来的每一个行组合,MYSQL检查使用哪个索引,并用它来从表中返回行。这是使用索引的最慢的连接之一

Using filesort 看到这个的时候,查询就需要优化了。MYSQL需要进行额外的步骤来发现如何对返回的行排序。它根据连接类型以及存储排序键值和匹配条件的全部行的行指针来排序全部行

Using index 列数据是从仅仅使用了索引中的信息而没有读取实际的行动的表返回的,这发生在对表的全部的请求列都是同一个索引的部分的时候

Using temporary 看到这个的时候,查询需要优化了。这里,MYSQL需要创建一个临时表来存储结果,这通常发生在对不同的列集进行ORDER BY上,而不是GROUP BY上

Where used 使用了WHERE从句来限制哪些行将与下一张表匹配或者是返回给用户,如果不想返回表中的全部行,并且连接类型ALL或index,这就会发生,或者是查询有问题.

不同连接类型的解释,按照效率高低的顺序排序

system 表只有一行:system表,这是const连接类型的特殊情况.

const 表中的一个记录的最大值能够匹配这个查询(索引可以是主键或惟一索引)。因为只有一行,这个值实际就是常数,因为MYSQL先读这个值然后把它当做常数来对待

eq_ref 在连接中,MYSQL在查询时,从前面的表中,对每一个记录的联合都从表中读取一个记录,它在查询使用了索引为主键或惟一键的全部时使用

ref 这个连接类型只有在查询使用了不是惟一或主键的键或者是这些类型的部分(比如,利用最左边前缀)时发生。对于之前的表的每一个行联合,全部记录都将从表中读出。这个类型严重依赖于根据索引匹配的记录多少—越少越好

range 这个连接类型使用索引返回一个范围中的行,比如使用>或<查找东西时发生的情况

index 这个连接类型对前面的表中的每一个记录联合进行完全扫描,比ALL更好,因为索引一般小于表数据.

ALL 这个连接类型对于前面的每一个记录联合进行完全扫描,这一般比较糟糕,应该尽量避免.

Tags: msyql Explain用法

分享到: