Mysql 層級、執行順序、執行計划分析


邏輯分層

下面是MySQL的邏輯分層圖:

連接層:連接與線程處理,這一層並不是MySQL獨有,一般的基於C/S架構的都有類似組件,比如連接處理、授權認證、安全等。

服務層:包括緩存查詢、解析器、優化器,這一部分是MySQL核心功能,包括解析、優化SQL語句,查詢緩存目錄,內置函數(日期、時間、加密等函數)的實現。

引擎層:負責數據存儲,存儲引擎的不同,存儲方式、數據格式、提取方式等都不相同,這一部分也是很大影響數據存儲與提取的性能的;對存儲層的抽象。

存儲層:存儲數據,文件系統。

 

存儲引擎

查看數據庫支持的存儲引擎:show engines;

如果要想查看數據庫默認使用哪個引擎,可以通過使用命令: show variables like '%storage_engine%';

InnoDB,MyISAM的主要區別:

InnoDB:在MySQL5.5開始作為默認的存儲引擎,支持事務,行級鎖,適合高並發場景,XA協議支持分布式事務,事務優先

MyISAM:不支持事務,性能優先,表級鎖,不適合高並發場景。

sql執行順序:https://www.cnblogs.com/annsshadow/p/5037667.html

 explain-執行計划

explain顯示了mysql如何使用索引來處理select語句以及連接表。可以幫助選擇更好的索引和寫出更優化的查詢語句。

使用方法,在select語句前加上explain就可以了:

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

EXPLAIN列的解釋:

id:情況有三種,分別是:id相同表示加載表的順序是從上到下。id不同id值越大,優先級越高,越先被執行。id有相同,也有不同,同時存在。id相同的可以認為是一組,從上往下順序執行;在所有的組中,id的值越大,優先級越高,越先執行。

table:顯示這一行的數據是關於哪張表的

type:這是重要的列,顯示連接使用了何種類型。

possible_keys:顯示可能應用在這張表中的索引。但是並不表示此索引會真正地被 MySQL 使用到,如果為空,沒有可能的索引。

key: 實際使用的索引。如果為NULL,則沒有使用索引。很少的情況下,MYSQL會選擇優化不足的索引。這種情況下,可以在SELECT語句中使用USE INDEX(indexname)來強制使用一個索引或者用IGNORE INDEX(indexname)來強制MYSQL忽略索引

key_len:使用的索引的長度。在不損失精確性的情況下,長度越短越好

ref:顯示索引的哪一列被使用了,如果可能的話,是一個常數

rows:MySQL 查詢優化器根據統計信息, 估算 SQL 要查找到結果集需要掃描讀取的數據行數.這個值非常直觀顯示 SQL 的效率好壞, 原則上 rows 越少越好.

Extra:關於MYSQL如何解析查詢的額外信息

select_type

select_type 表示了查詢的類型, 它的常用取值有:

  • SIMPLE, 表示此查詢不包含 UNION 查詢或子查詢

  • PRIMARY, 表示此查詢是最外層的查詢

  • UNION, 表示此查詢是 UNION 的第二或隨后的查詢

  • DEPENDENT UNION, UNION 中的第二個或后面的查詢語句, 取決於外面的查詢

  • UNION RESULT, UNION 的結果

  • SUBQUERY, 子查詢中的第一個 SELECT

  • DEPENDENT SUBQUERY: 子查詢中的第一個 SELECT, 取決於外面的查詢. 即子查詢依賴於外層查詢的結果.

最常見的查詢類別應該是 SIMPLE 了, 比如當我們的查詢沒有子查詢, 也沒有 UNION 查詢時, 那么通常就是 SIMPLE 類型

type

type 字段比較重要, 它提供了判斷查詢是否高效的重要依據依據. 通過 type 字段, 我們判斷此次查詢是 全表掃描 還是 索引掃描 等,(常見的)從最好到最差的連接類型為const、eq_reg、ref、range、index和ALL

  type顯示的是訪問類型,是較為重要的一個指標,結果值從好到壞依次是:system > const > eq_ref > ref > fulltext > ref_or_null > index_merge > unique_subquery > index_subquery > range > index > ALL
         一般來說,得保證查詢至少達到range級別,最好能達到ref。

  • system: 表中只有一條數據. 這個類型是特殊的 const 類型.

  • const: 針對主鍵或唯一索引的等值查詢掃描, 最多只返回一行數據. const 查詢速度非常快, 因為它僅僅讀取一次即可

  • eq_ref: 此類型通常出現在多表的 join 查詢, 表示對於前表的每一個結果, 都只能匹配到后表的一行結果. 並且查詢的比較操作通常是 =, 查詢效率較高.
  • ref: 此類型通常出現在多表的 join 查詢, 針對於非唯一或非主鍵索引, 或者是使用了 最左前綴(索引使用順序和定義順序一致) 規則索引的查詢.
  • range: 表示使用索引范圍查詢, 通過索引字段范圍獲取表中部分數據記錄. 這個類型通常出現在 =, <>, >, >=, <, <=, IS NULL, <=>, BETWEEN, IN() 操作中.
    typerange 時, 那么 EXPLAIN 輸出的 ref 字段為 NULL, 並且 key_len 字段是此次查詢中使用到的索引的最長的那個.(in查詢時有時候會失效,從而變成無索引All)
  • index: 表示全索引掃描(full index scan), 和 ALL 類型類似, 只不過 ALL 類型是全表掃描, 而 index 類型則僅僅掃描所有的索引, 而不掃描數據.
    index 類型通常出現在: 所要查詢的數據直接在索引樹中就可以獲取到, 而不需要掃描數據. 當是這種情況時, Extra 字段 會顯示 Using index.
  • ALL: 表示全表掃描, 這個類型的查詢是性能最差的查詢之一. 通常來說, 我們的查詢不應該出現 ALL 類型的查詢, 因為這樣的查詢在數據量大的情況下, 對數據庫的性能是巨大的災難. 如一個查詢是 ALL 類型查詢, 那么一般來說可以對相應的字段添加索引來避免.
  ALL 類型因為是全表掃描, 因此在相同的查詢條件下, 它是速度最慢的.而 index 類型的查詢雖然不是全表掃描, 但是它掃描了所有的索引, 因此比 ALL 類型的稍快.

Extra

EXplain 中的很多額外的信息會在 Extra 字段顯示, 常見的有以下幾種內容:

  • Using filesort
    當 Extra 中有 Using filesort 時, 表示 MySQL 需額外的排序操作, 不能通過索引順序達到排序效果. 一般有 Using filesort, 都建議優化去掉, 因為這樣的查詢 CPU 資源消耗大.

   例: SELECT * FROM order_info ORDER BY product_name;(索引是:`user_product_detail_index` (`user_id`, `product_name`, `productor`)
   但是上面的查詢中根據 product_name 來排序, 因此不能使用索引進行優化, 進而會產生 Using filesort.
   如果我們將排序依據改為 ORDER BY user_id, product_name, 那么就不會出現 Using filesort
  • Using index  "覆蓋索引掃描", 表示查詢在索引樹中就可查找所需數據, 不用掃描表數據文件, 往往說明性能不錯
  • Using temporary 查詢有使用臨時表, 一般出現於排序, 分組和多表 join 的情況, 查詢效率不高, 建議優化.

 優化小結:

  1.  最左前綴(索引使用順序和定義順序一致)
  2. 將含有in的范圍查詢放到where條件的最后,防止索引失效
  3. using where 需要回原表查詢,using index不需要回原表查詢
 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM