使用MySQL的Explain執(zhí)行計(jì)劃的方法(SQL性能調(diào)優(yōu))
前言
上篇文章講了MySQL架構(gòu)體系,了解到MySQL Server端的優(yōu)化器可以生成Explain執(zhí)行計(jì)劃,而執(zhí)行計(jì)劃可以幫助我們分析SQL語(yǔ)句性能瓶頸,優(yōu)化SQL查詢(xún)邏輯,今天就一塊學(xué)習(xí)Explain執(zhí)行計(jì)劃的具體用法。
1. explain的使用
使用EXPLAIN關(guān)鍵字可以模擬優(yōu)化器執(zhí)行SQL語(yǔ)句,分析你的查詢(xún)語(yǔ)句或是結(jié)構(gòu)的性能瓶頸。 在 select 語(yǔ)句之前增加 explain 關(guān)鍵字,MySQL 會(huì)在查詢(xún)上設(shè)置一個(gè)標(biāo)記,執(zhí)行查詢(xún)會(huì)返回執(zhí)行計(jì)劃的信息,并不會(huì)執(zhí)行這條SQL。
就比如下面這個(gè):

輸出這么多列都是干嘛用的?
其實(shí)大都是SQL語(yǔ)句的性能統(tǒng)計(jì)指標(biāo),先簡(jiǎn)單總結(jié)一下每一列的大致作用,下面詳細(xì)講一下:

2. explain字段詳解
下面就詳細(xì)講一下每一列的具體作用。
id列
id表示查詢(xún)語(yǔ)句的序號(hào),自動(dòng)分配,順序遞增,值越大,執(zhí)行優(yōu)先級(jí)越高。

id相同時(shí),優(yōu)先級(jí)由上而下:

select_type列
select_type表示查詢(xún)類(lèi)型,常見(jiàn)的有SIMPLE簡(jiǎn)單查詢(xún)、PRIMARY主查詢(xún)、SUBQUERY子查詢(xún)、UNION聯(lián)合查詢(xún)、UNION RESULT聯(lián)合臨時(shí)表結(jié)果等。

table列
table表示SQL語(yǔ)句查詢(xún)的表名、表別名、臨時(shí)表名。

partitions列
partitions表示SQL查詢(xún)匹配到的分區(qū),沒(méi)有分區(qū)的話(huà)顯示NULL。

type列
type表示表連接類(lèi)型或者數(shù)據(jù)訪(fǎng)問(wèn)類(lèi)型,就是表之間通過(guò)什么方式建立連接的,或者通過(guò)什么方式訪(fǎng)問(wèn)到數(shù)據(jù)的。
具體有以下值,性能由好到差依次是:
system > const > eq_ref > ref > ref_or_null > index_merge > range > index > ALL
system
當(dāng)表中只有一行記錄,也就是系統(tǒng)表,是 const 類(lèi)型的特列。

const
表示使用主鍵或者唯一性索引進(jìn)行等值查詢(xún),最多返回一條記錄。性能較好,推薦使用。

eq_ref
表示表連接使用到了主鍵或者唯一性索引,下面的SQL就用到了user表主鍵id。

ref
表示使用非唯一性索引進(jìn)行等值查詢(xún)。

ref_or_null
表示使用非唯一性索引進(jìn)行等值查詢(xún),并且包含了null值的行。

index_merge
表示用到索引合并的優(yōu)化邏輯,即用到的多個(gè)索引。

range
表示用到了索引范圍查詢(xún)。

index
表示使用索引進(jìn)行全表掃描。

ALL
表示全表掃描,性能最差。

possible_keys列
表示可能用到的索引列,實(shí)際查詢(xún)并不一定能用到。

key列
表示實(shí)際查詢(xún)用到索引列。

key_len列
表示索引所占的字節(jié)數(shù)。

每種類(lèi)型所占的字節(jié)數(shù)如下:
| 類(lèi)型 | 占用空間 |
|---|---|
| char(n) | n個(gè)字節(jié) |
| varchar(n) | 2個(gè)字節(jié)存儲(chǔ)變長(zhǎng)字符串,如果是utf-8,則長(zhǎng)度 3n + 2 |
| tinyint | 1個(gè)字節(jié) |
| smallint | 2個(gè)字節(jié) |
| int | 4個(gè)字節(jié) |
| bigint | 8個(gè)字節(jié) |
| date | 3個(gè)字節(jié) |
| timestamp | 4個(gè)字節(jié) |
| datetime | 8個(gè)字節(jié) |
| 字段允許為NULL | 額外增加1個(gè)字節(jié) |
ref列
表示where語(yǔ)句或者表連接中與索引比較的參數(shù),常見(jiàn)的有const(常量)、func(函數(shù))、字段名。
如果沒(méi)用到索引,則顯示為NULL:



rows列
表示執(zhí)行SQL語(yǔ)句所掃描的行數(shù)。

filtered列
表示按條件過(guò)濾的表行的百分比。

用來(lái)估算與其他表連接時(shí)掃描的行數(shù),row x filtered = 252004 x 10% = 25萬(wàn)行
Extra列
表示一些額外的擴(kuò)展信息,不適合在其他列展示,卻又十分重要。
Using where
表示使用了where條件搜索,但沒(méi)有使用索引。

Using index
表示用到了覆蓋索引,即在索引上就查到了所需數(shù)據(jù),無(wú)需二次回表查詢(xún),性能較好。

Using filesort
表示使用了外部排序,即排序字段沒(méi)有用到索引。

Using temporary
表示用到了臨時(shí)表,下面的示例中就是用到臨時(shí)表來(lái)存儲(chǔ)查詢(xún)結(jié)果。

Using join buffer
表示在進(jìn)行表關(guān)聯(lián)的時(shí)候,沒(méi)有用到索引,使用了連接緩存區(qū)存儲(chǔ)臨時(shí)結(jié)果。
下面的示例中user_id在兩張表中都沒(méi)有建索引。

Using index condition
表示用到索引下推的優(yōu)化特性。

知識(shí)點(diǎn)總結(jié)
本文詳細(xì)介紹了Explain使用方式,以及每種參數(shù)所代表的含義。無(wú)論是工作還是面試,使用Explain優(yōu)化SQL查詢(xún),都是必備的技能,一定要牢記。
SQL查詢(xún)優(yōu)化方式圖表:

到此這篇關(guān)于使用MySQL的Explain執(zhí)行計(jì)劃的方法(SQL性能調(diào)優(yōu))的文章就介紹到這了,更多相關(guān)MySQL Explain內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
MySQL存儲(chǔ)過(guò)程中變量的定義以及應(yīng)用詳解
MySQL變量定義和應(yīng)用是我們經(jīng)常會(huì)遇到的問(wèn)題,下面這篇文章主要給大家介紹了關(guān)于MySQL存儲(chǔ)過(guò)程中變量的定義以及應(yīng)用的相關(guān)資料,文章通過(guò)圖文介紹的非常詳細(xì),需要的朋友可以參考下2023-06-06
MySQL8.0?Command?Line?Client輸入密碼后出現(xiàn)閃退現(xiàn)象的原因以及解決方法總結(jié)
我們?cè)诎惭bMYSQL數(shù)據(jù)庫(kù)時(shí),經(jīng)常會(huì)出現(xiàn)一些問(wèn)題,下面這篇文章主要給大家介紹了關(guān)于MySQL8.0?Command?Line?Client輸入密碼后出現(xiàn)閃退現(xiàn)象的原因以及解決方法的相關(guān)資料,需要的朋友可以參考下2023-03-03
MySQL刪除binlog日志文件的三種實(shí)現(xiàn)方式
本文介紹了三種刪除MySQL binlog日志文件的方法,包含手動(dòng)刪除、使用SQL命令刪除和設(shè)置自動(dòng)清理,具有一定的參考價(jià)值,感興趣的可以了解一下2025-02-02
MySQL如何修改字段類(lèi)型和字段長(zhǎng)度
這篇文章主要介紹了MySQL如何修改字段類(lèi)型和字段長(zhǎng)度,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-06-06

