一條SQL語句在執行時,其底層經歷了哪些過程?
大致來說,MySQL 能夠分爲 Server 層和存儲引擎層兩部分(固然,首先還得通過客戶端)
多個存儲引擎共用一個server層 所以全部跨存儲引擎的功能都在這一層實現,好比存儲過程、觸發器、視圖等mysql
建表時若是不指定存儲引擎則默認使用的是InnoDB存儲引擎(MySQL5.5.5版本之前默認使用的是MyISAM引擎 TODO:兩者區別後續講解)sql
鏈接器
一條SQL語句從客戶端傳過來首先會建立一個鏈接,用username和password認證身份
鏈接完成後若是沒有其餘操做便處於空閒狀態 默認8h自動斷開空閒鏈接
鏈接還分爲長鏈接和短鏈接
長鏈接:持續使用同一個鏈接處理請求
短鏈接:一個鏈接僅執行幾回後便斷開,而後從新創建鏈接
由於建立鏈接的過程比較複雜,因此建議儘可能使用長鏈接
可是長鏈接太多有時候MySQL佔用內存漲的特別快,此時能夠考慮如下兩種方案:
1.按期斷開長鏈接或者執行一個佔用內存大的查詢後斷開鏈接從新鏈接後繼續下面的查詢
2.MySQL5.7以上版本能夠使用mysql_reset_connection命令來初始化鏈接資源,此操做不須要重連以及登陸驗證,就能夠將鏈接恢復到剛剛建立完的狀態緩存
查詢緩存
創建鏈接後先去查詢緩存
可是你們基本不用mysql的緩存功能
由於只要有對該表數據更新,表上的全部緩存都會清空而後從新建立緩存
因此通常默認不查緩存 但能夠使用select SQL_CACHE * from T where ID = 1按需查詢
PS.MySQL8.0直接將查詢緩存功能刪掉了優化
分析器
通過緩存器後來到分析器
先作詞法分析 分析出sql語句中的關鍵字
而後作語法分析 判斷是否有語法錯誤spa
優化器
通過分析後MySQL知道你要作什麼了,可是在實際執行以前還得通過優化器優化一下
在表中有多個索引的時候,由優化器來決定使用哪一個索引
或者有多表關聯(join)的時候決定鏈接順序 選擇效率高的方案
TODO:MySQL根據什麼選擇索引呢?後續解答server
執行器
執行器開始執行以前會驗證是否有讀/寫權限 沒有則返回權限錯誤
有的話就打開表調用指定的存儲引擎接口獲取執行結果集 返回給客戶端
TODO:存儲引擎內部機制後續講解索引