MySQL 使用explain分析sql語句的查詢效率(一)
MySQL explain用於分析sql 語句的執行及資料庫索引的使用。本文將致力於幫助大家充分理解explain所返回的各項引數,從而使大家快速掌握explain用法技巧。如果你在看其他教程或視訊後仍覺得雲裡霧裡。那麼請通讀本文。
用法
explain的用法相當簡潔,直接在sql語句前加上EXPLAIN 即可,例如:
EXPLAIN
select * FROM ec_stores_info where stores_id = 9
- 1
- 2
- 1
- 2
本語句將返回:
每行將得到id,select_type,table,type,possible_keys,key,key_len,ref,rows,Extra幾個引數。
其中與效率息息相關的則是type,key,ref,rows。
下面依次解析以上所有引數:
引數解析
id,select_type,table 用於定位查詢,表示本行引數所對應的sql查詢部分:
(1)id
SELECT識別符。這是SELECT的查詢序列號。不重要,需要注意的是,不要把id當成執行順序,這並不準確。
(2)select_type
SELECT型別,可以為以下幾種:
- SIMPLE: 指示非子查詢和union的簡單查詢。
select * from class
- 1
- 1
- PRIMARY: 指示在有子查詢的語句中最外面的select,主查詢。
- UNION: 指示在使用union語句的第二個或後面的select。
- DEPENDENT UNION: 子查詢union語句的第二個或後面的select。
- UNION RESULT : union語句的結果集。
- SUBQUERY:子查詢中的語句。與union相反理解就行了。
- DEPENDENT SUBQUERY:子查詢中第一個語句。
- DERIVED:派生表的SELECT(FROM子句的子查詢)。
(3)table
就是表名,本行記錄對應查詢所應用的表。可以通過table表名幫助定位查詢。
使用explain時,有時table欄位顯示的並不是表名,而是 derived2 或 derived3 等等。。。
即 derived x 代表的是id為x的查詢所得的結果集。例如:
EXPLAIN
SELECT so.storeorder_id,so.storeorder_sn,si.stores_name
from ec_stores_order so
INNER JOIN
(SELECT stores_id,stores_name from ec_stores_info where stores_creatorid=2) si
on so.store_id=si.stores_id
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 1
- 2
- 3
- 4
- 5
- 6
- 7
explain後所得:
由以上內容可知,id為2的記錄對應inner join後的子查詢1,第一條記錄所對應的table引數值derived2即為子查詢1的結果集。
案例
為幫助大家理解,請看2個案例:
(1)
EXPLAIN
SELECT o.storeorder_id,o.storeorder_sn,i.stores_name
from ec_stores_order o
INNER JOIN ec_stores_info i
on o.store_id = i.stores_id
- 1
- 2
- 3
- 4
- 5
- 1
- 2
- 3
- 4
- 5
本例中沒有子查詢,所以explain後將返回兩條簡單查詢記錄
兩條select_type均為SIMPLE,第一條table 為o 即 stores_order表的代號,所以判定第一條的引數為join前半段在stores_order表中檢索資料的過程,第二條則是通過store_id在stores_info表中獲取stores_name的過程。
(2)
將上例中sql語句改寫成如下等效sql:
EXPLAIN
SELECT o.storeorder_id,
o.storeorder_sn,(SELECT stores_name from ec_stores_info where stores_id=o.store_id) as stores_name
from ec_stores_order o
- 1
- 2
- 3
- 4
- 1
- 2
- 3
- 4
本條sql與上條sql效果相同,但是加入了子查詢,故而返回引數與上個案例完全不同:
select_type為DEPENDENT SUBQUERY的記錄毫無疑問就是括號內的子查詢部分嘍,另一條PRIMARY的記錄對應的當然就是主查詢 select … from ec_stores_order o啦~