一条简单的 SQL 查询语句到底经历了什么?
生活随笔
收集整理的這篇文章主要介紹了
一条简单的 SQL 查询语句到底经历了什么?
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
一、MySQL 基礎架構
整體來說 MySQL 主要分為兩個部分,一個部分是:Server 層,另一部分是:存儲引擎層。
其中 Server 層包括有連接器、查詢緩存、分析器、優化器、執行器等,存儲引擎層支持 InnoDB、MyISAM、Memory 等。
現在最常用的存儲引擎是 InnoDB,同時也是 MySQL 默認的存儲引擎。
通過分析器知道要做什么。
通過優化器知道怎么做。
通過執行器調用存儲引擎接口,進行數據的查詢。
俗話說:"一圖勝千言",我們還是來看下面這張流程圖吧。
注: MySQL 8.0 版本已經將查詢緩存功能移除了。
二、SQL 語句執行流程
1、情形一
下面我們通過一條 SQL 語句來分析它在 MySQL 中的執行流程:
例如:select * from user where name = "yxhsea";
首先,客戶端通過 TCP 的三次握手連接上 MySQL 服務,通過連接器進行權限驗證。
驗證通過之后,客戶端發送 SQL 語句到 MySQL 服務端,通過緩存器判斷是否緩存了 name 是 yxhsea 的數據,
如果命中緩存,則直接將結果返回給客戶端,否則,SQL 語句通過分析器進行詞法分析、語法分析,
將 select、from、where 這些關鍵字識別出來,把 user 識別為表名,name 識別為列名。
之后,SQL 語句通過優化器選擇合適的索引,生成具體的執行計劃。
最后,SQL 語句到達執行器調用存儲引擎的查詢接口,將查詢到的數據返回給客戶端。
2、情形二
我們分析下面這條 SQL 語句的執行流程:
select id from user where age between 10 and 20;
1、首先,在 age 索引樹上找到 age 等于 10 的節點。
2、然后,再到 age 索引樹上繼續尋找下一個節點,直到 age 大于 20 時循環結束。
3、最后,返回 age 是 10 到 20 之間的查詢結果。
上面這種情況,屬于覆蓋索引。
顧名思義,覆蓋索引就是要查詢的數據就存儲在索引樹上,不需要進行回表操作。
3、情形三
那什么情況下就需要進行回表呢?我們來分析下面這條 SQL 語句:
select * from user where age between 10 and 20;
1、首先,在 age 索引樹上找到 age 等于 10 的節點,獲取到 ID 等于 1。
2、然后,到 ID 索引樹上找到 ID 等于 1 的節點,獲取行記錄。
3、之后,再回到 age 索引樹上,尋找下一個節點 age 等于 20,獲取到 ID 等于 2 (再重復第 2 步)。
4、依次類推 (再重復第 1、2 步),循環遍歷直到 age 大于 20 時,循環結束。
5、最后,將在 ID 索引樹上查詢到的行記錄作為結果返回。
這里的流程當中的,回到 ID 索引樹上查詢行記錄的過程,稱之為回表。
注:使用 * 查詢數據會導致回表,所以我們在查詢數據的時候,盡量指定具體的字段覆蓋索引。
四、結語
我們在這里介紹了 MySQL 的基本架構,以及一條簡單 SQL 語句的執行流程。因此我們在平常編寫 SQL 語句的過程中,應該盡量使用覆蓋索引的方式,來避免回表查詢造成額外的磁盤開銷。當然這篇文章也只是介紹了 SQL 語句執行流程的一小分部內容,其中涉及到鎖、事務等并未展開講述。以上純是我的淺知拙見,如有不妥,敬請斧正。
總結
以上是生活随笔為你收集整理的一条简单的 SQL 查询语句到底经历了什么?的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 《NVMe-over-Fabrics-1
- 下一篇: 抽取JDBC工具类