mysql explain的用法

MySQL的EXPLAIN命令顯示了mysql如何使用索引來處理select語句以及連接表墨坚⊙硪可以幫助選擇更好的索引和寫出更優(yōu)化的查詢語句。
一泽篮、通過expalin可以得到
1盗尸、表的讀取順序
2、表的讀取操作的操作類型
3帽撑、哪些索引可以使用
4泼各、哪些索引被實際使用
5、表之間的引用
6油狂、每張表有多少行被優(yōu)化器查詢

二历恐、如何調(diào)用expalin命令

1、只需要在SELECT前面加上EXPLAIN即可专筷,例如

explain select surname,first_name form a,b where a.id=b.id 

2弱贼、在語句結(jié)尾(;之前)加上\G能夠更清晰的查看.
3、需要說的是EXPLAIN只對SELECT查詢作解釋,INSERT,UPDATE,DELETE不會

三磷蛹、explain顯示的列
1吮旅、id
語句的執(zhí)行順序標識,如果在語句中沒有子查詢或聯(lián)合,說明只有一個SELECT,于是這個列顯示為1,否則內(nèi)層的SELECT會順序編號.

2味咳、select_type
顯示了對應的查詢是簡單還是復雜SELECT庇勃,主要有以下幾種查詢類型

1)、simple 簡單類型
語句中沒有子查詢或union

2)槽驶、primary
最外層的select 责嚷,不是主鍵
這是為更復雜的查詢而創(chuàng)建的首要表(也就是最外層的表)。這個類型通车囝恚可以在DERIVED 和UNION 類型混合使用時見到罕拂。

3)、union
union是在select 語句中第二個select語句后面所有的select全陨,第一個select 為primary
這是UNION 語句其中的一個SQL 元素爆班。

4)、dependent subquery
子查詢中內(nèi)層中第一個select語句
這個select-type 值是為使用子查詢而定義的辱姨。下面的SQL語句提供了這個值: mysql> EXPLAIN SELECT p.* -> FROM parent p -> WHERE p.id NOT IN (SELECT c.parent_id FROM child c);

5)柿菩、dependent union
子查詢中union且為union中第二個select開始的后面所有select,依賴于外部的結(jié)果集雨涛。

6)枢舶、SUBQUERY
子查詢內(nèi)層查詢的第一個SELECT懦胞,結(jié)果不依賴于外部查詢結(jié)果集。

7)祟辟、devived
派生表的查詢語句
當一個表不是一個物理表時医瘫,那么就被叫做DERIVED。下面的SQL 語句給出了一個QEP 中DERIVED select-type 類型的
示例:

 mysql> EXPLAIN SELECT MAX(id)
 -> FROM (SELECT id FROM users WHERE first = 'west') c;

8)旧困、uncacheable subquery
結(jié)果集無法緩存的子查詢

9)醇份、union result
union中合并的結(jié)果
這是一系列定義在UNION 語句中的表的返回結(jié)果。當select_type 為這個值時吼具,經(jīng)沉欧祝可以看到table 的值是<unionN,M>, 這說明匹配的id 行是這個集合的一部分拗盒。下面的SQL產(chǎn)生了一個UNION和UNION RESULT select-type:

mysql> EXPLAIN SELECT p.* FROM parent p WHERE p.val LIKE 'a%' 
-> UNION 
-> SELECT p.* FROM parent p WHERE p.id > 5;

**3怖竭、table **

1)、顯示對應行正在訪問哪個表
2)陡蝇、當FROM子句中有子查詢或UNION時,table列是<derivedN>,其中N是id列對應的值

**4痊臭、type **
聯(lián)合查詢所使用的類型,type顯示的是訪問類型登夫,是較為重要的一個指標广匙,結(jié)果值從好到壞依次是:
system > const > eq_ref > ref >fulltext > ref_or_null > index_merge > unique_subquery >index_subquery > range > index > ALL

一般來說,得保證查詢至少達到range級別恼策,最好能達到ref鸦致。

這列很重要,顯示了連接使用了哪種類別,有無使用索引。主要包括以下幾種類型

1)涣楷、all
全表掃描分唾,效果是最不理想的。
2)狮斗、const
const是在where條件以常量作為查詢條件绽乔,最多只會有一條記錄匹配,由于是常量碳褒,實際上只須要讀一次迄汛。
3)、eq_ref
最多只會有一條匹配結(jié)果骤视,一般是通過主鍵或唯一鍵索引來訪問。一般會出現(xiàn)在連接查詢的語句中鹃觉。
4)专酗、fulltext
進行全文索引檢索。
5)盗扇、index
全索引掃描祷肯。MySQL在掃描表時按索引次序進行而不是行沉填。
6)、index_merge
查詢中同時使用兩個(或更多)索引佑笋,然后對索引結(jié)果進行合并(merge)翼闹,再讀取表數(shù)據(jù)。
7)蒋纬、index_subquery
子查詢中的返回結(jié)果字段組合是一個索引(或索引組合)猎荠,但不是一個主鍵或唯一索引。
8)蜀备、rang
索引范圍掃描关摇。一個有限制的索引掃描,它開始于索引里的某一點,返回匹配這個值域的行(顯而易見的范圍掃描.即帶有BETWEEN或在WHERE子句中帶有>的查詢,當MySQL使用索引去查找一系列值的時候,如IN()和OR列表,也為顯示的范圍掃描)
9)碾阁、ref
也叫索引查找,他返回所有匹配某單個值的行,它可能會找到多個符合條件行输虱。
10)、ref_or_null
與ref的唯一區(qū)別就是在使用索引引用的查詢之外再增加一個空值的查詢脂凶。
11)宪睹、system
系統(tǒng)表,表中只有一行數(shù)據(jù)蚕钦;
12)亭病、unique_subquery
子查詢中的返回結(jié)果字段組合是主鍵或唯一約束。

5冠桃、possible_keys
這一列顯示了查詢可以使用哪些索引,是基于查詢訪問的列和使用的比較操作符來判斷的.
如果沒有任何索引可以使用命贴,就會顯示成null

6、key
顯示了MySQL決定采用哪個索引來優(yōu)化對該表的訪問

7食听、key_len
1)胸蛛、key_len列顯示mysql決定使用的鍵長度,如果鍵是null樱报,則長度為null葬项。
2)、顯示MySQL在索引里使用的字節(jié)數(shù).舉個例子就是在查詢中使用到了主鍵,而主鍵的數(shù)據(jù)類型為INT,則為4,SMALLINT則為2
3)迹蛤、使用的索引長度民珍,一般越短越好。

key_len 列定義了用于SQL 語句的連接條件的鍵的長度盗飒。此列值對于確認索引的有效性以及多列索引中用到的列的數(shù)目很重要嚷量。
此列的一些示例值如下所示: 此列的一些示例值如下所示:
key_len: 4 // INT NOT NULL
key_len: 5 // INT NULL
key_len: 30 // CHAR(30) NOT NULL
key_len: 32 // VARCHAR(30) NOT NULL
key_len: 92 // VARCHAR(30) NULL CHARSET=utf8

從這些示例中可以看出,是否可以為空逆趣、可變長度的列以及key_len 列的值只和用在連接和WHERE 條件中的索引的列 有關(guān)蝶溶。索引中的其他列會在ORDER BY 或者GROUP BY 語句中被用到。下面這個來自于著名的開源博客軟件WordPress 的表展示了 如何以最佳方式使用帶有定義好的表索引的SQL 語句:

CREATE TABLE `wp_posts` (  
 `ID` bigint(20) unsigned NOT NULL AUTO_INCREMENT,  
 `post_date` datetime NOT NULL DEFAULT '0000-00-00 00:00:00',  
 `post_status` varchar(20) NOT NULL DEFAULT 'publish' ,  
 `post_type` varchar(20) NOT NULL DEFAULT 'post',  
 PRIMARY KEY (`ID`),  
 KEY `type_status_date`(`post_type`,`post_status`,`post_date`,`ID`)  
) DEFAULT CHARSET=utf8  
  
 CREATE TABLE `wp_posts` (  
 `ID` bigint(20) unsigned NOT NULL AUTO_INCREMENT,  
 `post_date` datetime NOT NULL DEFAULT '0000-00-00 00:00:00',  
 `post_status` varchar(20) NOT NULL DEFAULT 'publish' ,  
 `post_type` varchar(20) NOT NULL DEFAULT 'post',  
 PRIMARY KEY (`ID`),  
 KEY `type_status_date`(`post_type`,`post_status`,`post_date`,`ID`)  
) DEFAULT CHARSET=utf8  

這個表的索引包括post_type、post_status抖所、post_date 以及ID列梨州。下面是一個演示索引列用法的SQL 查詢: EXPLAIN SELECT ID, post_title FROM wp_posts WHERE post_type='post' AND post_date > '2010-06-01'; 這個查詢的QEP 返回的key_len 是62。這說明只有post_type列上的索引用到了(因為(20×3)+2=62)田轧。盡管查詢在WHERE 語句 中使用了post_type 和post_date 列暴匠,但只有post_type 部分被用到了。其他索引沒有被使用的原因是MySQL 只能使用定義索引的 最左邊部分傻粘。為了更好地利用這個索引每窖,可以修改這個查詢來調(diào)整索引的列。請看下面的示例:

mysql> EXPLAIN SELECT ID, post_title  
-> FROM wp_posts  
-> WHERE post_type='post'  
-> AND post_status='publish'  
-> AND post_date > '2010-06-01';  

在SELECT查詢的添加一個post_status 列的限制條件后抹腿,QEP顯示key_len 的值為132岛请,這意味著post_type、post_status警绩、post_date 三列(62+62+8崇败,(20×3)+2,(20×3)+2肩祥,8)都被用到了后室。此外,這個索引的主碼列ID 的定義是使用MyISAM 存儲索 引的遺留痕跡混狠。當使用InnoDB 存儲引擎時岸霹,在非主碼索引中包含主碼列是多余的,這可以從key_len 的用法看出來将饺。 相關(guān)的QEP 列還包括帶有Using index 值的Extra 列贡避。

8、Ref
顯示了之前的表在key列記錄的索引中查詢值所用到的列或常量
予弧。

9刮吧、rows
顯示的是MySQL為了找到所需的值而要讀取的行數(shù).

10、extra
在此顯示的是在其他列不適合顯示的額外信息
掖蛤,主要可能會是以下內(nèi)容:
1)杀捻、Distinct
查找distinct 值,當mysql找到了第一條匹配的結(jié)果時蚓庭,將停止該值的查詢致讥,轉(zhuǎn)為后面其他值查詢。

2)器赞、Full scan on NULL key
子查詢中的一種優(yōu)化方式垢袱,主要在遇到無法通過索引訪問null值的使用。

3)港柜、Using index
表優(yōu)化器只需要通過訪問索引就可以獲取到需要的數(shù)據(jù)

4)惶桐、Using where
表示優(yōu)化器需要通過索引回表查詢數(shù)據(jù)(需要通過訪問數(shù)據(jù)塊獲取結(jié)果集)

5)、Using temporary
意味著MySQL在對查詢結(jié)果排序時會用到一個臨時表.
這個值表示使用了內(nèi)部臨時(基于內(nèi)存的)表。一個查詢可能 用到多個臨時表姚糊。有很多原因都會導致MySQL 在執(zhí)行查詢期間 創(chuàng)建臨時表。兩個常見的原因是在來自不同表的列上使用了 DISTINCT授舟,或者使用了不同的ORDER BY 和GROUP BY 列救恨。 想了解更多內(nèi)容可以訪問http://forge.mysql.com/wiki/Overview_ of_query_execution_and_use_of_temp_tables。 可以強制指定一個臨時表使用基于磁盤的MyISAM 存儲引 擎释树。這樣做的原因主要有兩個: ? 內(nèi)部臨時表占用的空間超過min(tmp_table_size肠槽,max_ heap_table_size)系統(tǒng)變量的限制 ? 使用了TEXT/BLOB 列

6)、Using filesort
看到這個的時候奢啥,查詢就需要優(yōu)化了秸仙。意味著MySQL會對結(jié)果使用一個外部索引排序,而不是按索引次序從表里讀出來.
這是ORDER BY 語句的結(jié)果。這可能是一個CPU 密集型的過程桩盲。 可以通過選擇合適的索引來改進性能寂纪,用索引來為查詢結(jié)果排序。詳細過程請參考第4 章赌结。

7). Using join buffer
這個值強調(diào)了在獲取連接條件時沒有使用索引捞蛋,并且需要連接緩沖區(qū)來存儲中間結(jié)果。 如果出現(xiàn)了這個值柬姚,那應該注意拟杉,根據(jù)查詢的具體情況可能需要添加索引來改進性能。
這篇博客中有Using join buffer的詳細說明
https://my.oschina.net/xinxingegeya/blog/495897

這篇博客中有join的詳細說明
http://blog.csdn.net/tonyxf121/article/details/7796657

8). Impossible where
這個值強調(diào)了where 語句會導致沒有符合條件的行量承。請看下面的示例: mysql> EXPLAIN SELECT * FROM user WHERE 1=2;

9). Select tables optimized away
這個值意味著僅通過使用索引搬设,優(yōu)化器可能僅從聚合函數(shù)結(jié)果中返回一行

10). Index merges
當MySQL 決定要在一個給定的表上使用超過一個索引的時候,就會出現(xiàn)以下格式中的一個撕捍,詳細說明使用的索引以及合并的類型拿穴。
? Using sort_union(...)
? Using union(...)
? Using intersect(...)

11). Using where, Using index .....
說明該查詢有部分數(shù)據(jù)需要通過回表方式獲取有部分數(shù)據(jù)可以直接通過索引獲取

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市卦洽,隨后出現(xiàn)的幾起案子贞言,更是在濱河造成了極大的恐慌,老刑警劉巖阀蒂,帶你破解...
    沈念sama閱讀 221,695評論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件该窗,死亡現(xiàn)場離奇詭異,居然都是意外死亡蚤霞,警方通過查閱死者的電腦和手機酗失,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,569評論 3 399
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來昧绣,“玉大人规肴,你說我怎么就攤上這事。” “怎么了拖刃?”我有些...
    開封第一講書人閱讀 168,130評論 0 360
  • 文/不壞的土叔 我叫張陵删壮,是天一觀的道長。 經(jīng)常有香客問我兑牡,道長央碟,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 59,648評論 1 297
  • 正文 為了忘掉前任均函,我火速辦了婚禮亿虽,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘苞也。我一直安慰自己洛勉,他們只是感情好,可當我...
    茶點故事閱讀 68,655評論 6 397
  • 文/花漫 我一把揭開白布如迟。 她就那樣靜靜地躺著收毫,像睡著了一般。 火紅的嫁衣襯著肌膚如雪氓涣。 梳的紋絲不亂的頭發(fā)上牛哺,一...
    開封第一講書人閱讀 52,268評論 1 309
  • 那天,我揣著相機與錄音劳吠,去河邊找鬼引润。 笑死,一個胖子當著我的面吹牛痒玩,可吹牛的內(nèi)容都是我干的淳附。 我是一名探鬼主播,決...
    沈念sama閱讀 40,835評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼蠢古,長吁一口氣:“原來是場噩夢啊……” “哼奴曙!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起草讶,我...
    開封第一講書人閱讀 39,740評論 0 276
  • 序言:老撾萬榮一對情侶失蹤洽糟,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后堕战,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體坤溃,經(jīng)...
    沈念sama閱讀 46,286評論 1 318
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 38,375評論 3 340
  • 正文 我和宋清朗相戀三年嘱丢,在試婚紗的時候發(fā)現(xiàn)自己被綠了薪介。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 40,505評論 1 352
  • 序言:一個原本活蹦亂跳的男人離奇死亡越驻,死狀恐怖汁政,靈堂內(nèi)的尸體忽然破棺而出道偷,到底是詐尸還是另有隱情,我是刑警寧澤记劈,帶...
    沈念sama閱讀 36,185評論 5 350
  • 正文 年R本政府宣布勺鸦,位于F島的核電站,受9級特大地震影響目木,放射性物質(zhì)發(fā)生泄漏祝旷。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,873評論 3 333
  • 文/蒙蒙 一嘶窄、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧距贷,春花似錦柄冲、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,357評論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至阁最,卻和暖如春戒祠,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背速种。 一陣腳步聲響...
    開封第一講書人閱讀 33,466評論 1 272
  • 我被黑心中介騙來泰國打工姜盈, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人配阵。 一個月前我還...
    沈念sama閱讀 48,921評論 3 376
  • 正文 我出身青樓馏颂,卻偏偏與公主長得像,于是被迫代替她去往敵國和親棋傍。 傳聞我的和親對象是個殘疾皇子救拉,可洞房花燭夜當晚...
    茶點故事閱讀 45,515評論 2 359

推薦閱讀更多精彩內(nèi)容