MySQL使用EXPLAIN分析SQL
EXPLAIN 關鍵字詳解
使用EXPLAIN 關鍵字可以模擬優化器執行SQL 查詢語句,從而知道MySQL數據庫是如何處理你的SQL 語句的。因此我們可以使用該關鍵字知道我們編寫的SQL 語句是否是高效的,從而可以提高我們程序猿編寫SQL 的能力。
使用EXPLAIN 關鍵字可以讓我們知道表的讀取順序、數據讀寫操作的操作類型、哪些索引是可以使用的、哪些索引是實際使用的、表之間的引用、每張表有哪些行被MySQL優化器查詢。其基本的使用語法是EXPLAIN + SQL 語句。
在這里我使用EXPLAIN 關鍵字執行了一條SQL 語句
EXPLAIN SELECT * FROM t_dept WHERE dept_id = (SELECT dept_id FROM t_emp WHERE emp_id=177);下面是執行該語句所輸出的結果:
我們可以看出查詢結果包含了很多字段,下面我們就來了解一下這些字段都是什么意思。
EXPLAIN 字段詳解
id:SELECT 查詢的序列號,表示查詢中執行的SELECT 子句或操作表的順序,id 表現的形式有三種:
1]:id相同,執行順序由上至下。
2]:id 不同,如果是子查詢,id 的序號會遞增,id 的值越大優先級越高,越先被執行。
3]:id 既有相同的又有不同的,即id 值越大的優先被執行,如果存在id 相同的,則在上面的執行順序高于在下面的。
所以MySQL對于我們編寫的SQL 語句并不是按照我們編寫的順序執行,這一點與我們的四則運算順序相類似,并不是在最前面的運算先執行,要考慮運算符與括號的問題。
select_type:首先select_type 有好幾種,表示查詢的類型,主要用于區別普通查詢,聯合查詢,子查詢等復雜查詢。下面逐一介紹:
| SIMPLE | 簡單的SELECT 查詢,查詢中不包括子查詢或者UNION |
| PRIMARY | 查詢中若包含任何復雜的子查詢,最外層的查詢會被標記為PRIMARY |
| SUBQUERY | 在SELECT 或 WHERE 列表中包含的子查詢部分(可以參照上面查詢的結果) |
| DERIVED | 在FROM 列表中包含的子查詢被標記為DERIVED (衍生),MySQL會遞歸執行這些子查詢,把結果放在臨時表里 |
| UNION | 若第二個SELECT 出現在UNION 之后,就會被標記為UNION,若UNION 包含在FROM 字句的子查詢中,外層的SELECT 將被標記為:DERIVED |
| UNION RESULT | 從UNION 表中獲取結果的 SELECT |
table:表示這一行數據關聯的數據表。
partitions:表示給定表所使用的分區。
type:表示查詢語句的連接類型。type 也有很多種,下面做具體介紹:
| system | 表只有一行(相當于系統表),這是const 類型的特例,一般很少出現 |
| const | 表示通過索引一次就可以查詢到數據,用于比較primary key 或者unique 索引。如果將主鍵置于WHERE 條件中,MySQL就將該查詢轉換位一個常量 |
| eq_ref | 唯一性索引掃描,對于每個索引鍵,表中只有一條記錄相匹配,常用于主鍵或唯一索引掃描 |
| ref | 非唯一性索引掃描,返回匹配某個單獨值的所有行,本質上也是一種索引訪問,返回的是所有匹配某個單獨之的行,屬于查找和掃描的混合體 |
| range | 只檢索給定范圍的行,使用一個索引來選擇行。比如在WHERE 語句中出現的BETWEEN 、IN 等的查詢。這種索引的掃描范圍比全表掃描要好 |
| index | 所有索引掃描,index 與all 的最大區別是index 類型只掃描索引樹。這通常比all 塊,因為索引文件通常比數據文件要小 |
| all | 遍歷全表找到匹配的行(是從磁盤中讀取數據) |
type 的類型不止上面的幾種,這里只列出了比較常見的幾種類型, 根據上面的介紹我們總結出從出現的最好到最差的順序是:system > const > eq_ref > ref > range > index > all ,但是對于一般來說,能夠保證達到range 級別就可以了,最好達到ref 級別。
possible_keys: 表示在這張表可能會使用的索引,一個或多個,只是可能會使用,但是不表示一定被實際使用。
key:實際上使用的索引。可以為null 表示沒有使用索引。
key_len:表示索引中的字節數,可以通過該列計算查詢中使用的索引的長度。在不失精度的情況下,長度越短越好。key_len 顯示的值為索引字段的最大可能長度,并非實際長度,是根據表定義計算得出。
ref:顯示索引的哪一列被使用了,一般是一個常數。
rows:根據表統計信息及選取索引的情況,大致估算出查到記錄所需要讀取的行數。
filtered:filtered列給出了一個百分比的值,這個百分比值和rows列的值一起使用,可以估計出那些將要和QEP中的前一個表進行連接的行的數目。
extra:包含不適合在其他列中顯示但是也十分重要的額外信息:
| Using filesort | 說明MySQL會對數據使用一個外部的索引排序,而不是按照表內的索引順序進行讀取。MySQL無法利用索引完成的排序操作被稱為“文件排序”。這種情況是極其糟糕的 |
| Using temporary | 使用了臨時表保存中間結果,MySQL在對查詢結果排序時使用臨時表, 主要是order by 和分組查詢。這種情況的出現也是極其糟糕的 |
| Using index | 表示相應的查詢字段覆蓋了索引,避免了訪問表的數據行,效率很高。 |
| Using where | 表示使用了WHERE 進行過濾 |
| Using join where | 表示使用了連接緩存 |
| impossible where | 表示WHERE 子句的值永遠為false ,不能用來獲取數據 |
| distinct | 優化distinct 操作,表示在找到第一匹配的元組后就停止找同樣的值 |
總結
以上是生活随笔為你收集整理的MySQL使用EXPLAIN分析SQL的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: u盘格式化变小了怎么办 U盘变小了怎么办
- 下一篇: MySql小表驱动大表