Sql優化之explain

sql優化是高級工程師必修課,對于百萬級以上的數據,要避免全表掃描,可以借助一些分析工具查看sql執行過程,進而優化sql

explain顯示了MySQL如何使用索引來處理select語句以及連接表。可以通過模擬mysql的優化器幫助選擇更好的索引和寫出更優化的查詢語句。
首先,我們來明確下explain能干嘛 ?

  • 表的讀取順序
  • 數據讀取操作的操作類型
  • 哪些索引可以使用
  • 哪些索引被實際使用
  • 表之間的引用
  • 每張表有多少行被優化器查詢
  • 說了這么多使用explain的好處,那么實際上到底該怎么玩? 答案: explain + 待執行的sql

從上表中我們看到,通過explain+sql執行后,顯示了一張列表,那么接下來我們就詳細說說這個個列表中表頭各個字段的意思,只有先明確了各個字段的意思,才能知道sql 的優劣程度!


1. id:決定表的讀取順序
執行select 語句查詢的序列號,包含一組數字,表示查詢中執行select子句或操作表的順序
它有三種情況:

  • id相同,執行順序由上至下;
  • id不同,如果是子查詢,id的序號會遞增,id值越大優先級越高,越先被執行;
  • id相同不同,同時存在,如果id相同,可以認為是一組,從上往下順序執行,在所有組中,id值越大,優先級越高,越先執行;

2. select_type:查詢的類型,也就是數據讀取操作的操作類型,他一共有以下5種:

1. simple:簡單的select查詢,查詢中不包含子查詢或者union;

2. primary/union:

  • primary:查詢中最外層的SELECT(如兩表做UNION或者存在子查詢的外層的表操作為PRIMARY,內層的操作為UNION)
  • union:union操作中,查詢中處于內層的select(內層的select語句與外層的select語句沒有依賴關系)

3. dependent union / union result:

  • dependent union:union操作中,查詢中處于內層的select(內層的select語句與外層的select語句有依賴關系)
  • union result:union 操作的結果,id值通常為null

4. subquery / dependent subquery:

  • subquery:子查詢中首個select(如果有多個子查詢存在)
  • dependent subquery:子查詢中首個SELECT,但依賴于外層的表(如果有多個子查詢存在)

5. derived/MATERIALIZED:

  • derived:在from列表中包含的子查詢被標記為DERIVED(衍生表),mysql會遞歸執行這些子查詢,把結果放臨時表中;
  • MATERIALIZED:被物化的子查詢

6. UNCACHEABLE SUBQUERY/UNCACHEABLE UNION:

  • UNCACHEABLE SUBQUERY:對于外層的主表,子查詢不可被物化,每次都需要計算(耗時操作)
  • UNCACHEABLE UNION:UNION操作中,內層的不可被物化的子查詢(類似于UNCACHEABLE SUBQUERY)

3. type:訪問類型排列
顯示查詢使用了何種類型,從最好到最差依次是:system > const > eq_ref > ref > range > index > all
explain 的type類型的理解

  • system:表只有一行記錄(等于系統表),這是const類型的特例,平時不會出現,這個也可忽略不計;
  • const:表示通過索引一次就找到了,const用于比較primary key或者unique索引。因為只匹配一行記錄,所以很快. 如果將主鍵置于>- where列表中,mysql就能將該查詢轉換成一個常量;
  • eq_ref:唯一性索引掃描,對于每一個索引鍵,表中只有一條記錄與之匹配,常用于主鍵或唯一索引掃描;
  • ref:非唯一性索引掃描,返回匹配某個單獨值得所有行,本質上也是一種索引訪問,它返回所有匹配某個單獨值的行,然而,它可能會找到多個符合條件的行,所以它應該屬于查找和掃描的混合體;
  • range:只檢索給定范圍的行,使用一個索引來選擇行,key列顯示使用哪個索引,一般就是在你的where語句中出現了between,<,>,in等的查詢;這種范圍索引掃描比全表掃描要好,因為它只需要開始于索引的某一個點,結束于另一個點,不用掃描全部索引;
  • index:index于all區別為index類型只遍歷索引樹,這通常比all快,因為索引文件通常比數據文件小;也就是說雖然all和index都是讀寫表,但index是從索引中讀取的,而all是從硬盤中讀的;
  • all:也就是全表掃描;
    備注:一般來說,得保證查詢至少達到range級別,最好能達到ref.

4. possible_keys:顯示可能會被應用到這張表的索引,一個或者多個;查詢涉及到的字段上若存在索引,則該索引將被列出,但不一定被查詢實際使用到;


5. key:實際使用到的索引.如果為null,則沒有使用索引;查詢中若使用了覆蓋索引,則該索引僅出現在key列表中;


6. key_len:表示索引中使用的字節數,可通過該列計算查詢中使用的索引的長度,在不損失精確性的情況下,長度越短越好; key_len顯示的值為索引字段的最大可能長度,并非實際使用長度,即key_len是根據表定義計算而得,不是通過表內檢索出的;


7. ref:顯示索引的哪一列被使用了,如果可能的話,是一個常數,哪些列或常量別用于查找索引列上的值;


8. rows:根據表統計信息及索引選用情況,大致估算出找到所需的記錄所需要讀取的行數;


9. Extra:包含不適合在其它列中顯示但十分重要的額外信息:

  • using filesort(出現這個東西不好):說明mysql中無法利用索引來完成排序,這時候使用文件排序。其效率很低

  • using temporary(出現這個東西更不好,使用到了臨時表):使用了臨時表保存中間結果,Mysql在對查詢結果排序時使用臨時表,常見于排序order by和分組查詢group by.

  • using index:表示相應的select操作中使用了覆蓋索引(Covering Index),避免了訪問了表的數據行,效率不錯!

如果同時出現using where ,表明索引被用來執行索引鍵值的查找;
如果沒有同時出現using where,表明索引用來讀取數據而非執行查找操作;

  • using where:使用了where
  • using join buffer:使用了連接緩存;
  • impossible where:where 子句的值總是false,不能用來獲取任何元素;
  • select tables optimized away:在沒有group by子句的情況下,基于索引優化MIN/MAX操作或者對于MyISAM存儲引擎優化count(*)操作,不必等到執行階段再進行計算,查詢執行計劃生成的階段即完成優化;
  • distinct :去掉重復的數據

轉載:http://www.lxweimin.com/p/d4863178b4f8

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 227,702評論 6 531
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 98,143評論 3 415
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 175,553評論 0 373
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 62,620評論 1 307
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 71,416評論 6 405
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 54,940評論 1 321
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,024評論 3 440
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 42,170評論 0 287
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 48,709評論 1 333
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 40,597評論 3 354
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 42,784評論 1 369
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 38,291評論 5 357
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,029評論 3 347
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 34,407評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 35,663評論 1 280
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 51,403評論 3 390
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 47,746評論 2 370