文章公號 首發!連載中~ 歡迎各位大佬關注, 回覆:「抽獎」 還可參加抽📖活動 html
文末有二維碼 mysql
回顧一下以前和你們分享的知識點golang
看了前面的文章,想必你確定瞭解了什麼是Buffer Pool、LRU-List、Free-List、Flush-List,你也知道了當MySQL增刪改查時,內存中發生了什麼,以及這幾個雙向鏈表是如何配合工做的。面試
經過閱讀上一篇文章你也必定了解了:你create出來的table實際上是屬於一個表空間的,而所謂的表空間其實對應着一個真實存在於物理磁盤上的文件。sql
而且在前面的文章中,白日夢曾不止一次的說起到:InnoDB從磁盤中讀取數據的最小單位是數據頁。而你想獲得的id = xxx的數據,就是這個數據頁衆多行中的一行。數據庫
下面咱們就一塊兒看下,究竟什麼是MySQL的數據頁、數據區等概念。緩存
數據頁長下面這樣:優化
在MySQL的設定中,同一個表空間內的一組連續的數據頁爲一個extent(區),默認區的大小爲1MB,頁的大小爲16KB。16*64=1024,也就是說一個區裏面會有64個連續的數據頁。連續的256個數據區爲一組數據區。3d
因而咱們能夠畫出這張圖:htm
從直觀上看,其實不用納悶爲啥MySQL按照這樣的方式組織存儲在磁盤上的數據。
這就比如你搞了個Java的封裝類描述一類東西,而後再相應的給它加上一些功能方法,或者用golang封裝struct去描述一類對象。最終的目的都是爲了方便、管理、控制。
約定好了數據的組織方式,那MySQL的做用不就是:按照約定數據規則將數據文件中的數據加載進內存,而後展現給用戶看,以及提供其餘能力嗎?
假設你如今已經有兩個數據頁了。而且你正在往第二個數據頁中寫數據。
關於B+Tree,你確定知道B+Tree中的葉子結點之間是經過雙向鏈表關聯起來的。
在InnoDB索引的設定中,要求主鍵索引是遞增的,這樣在構建索引樹的時候才更加方便。你能夠腦補一下。若是按一、二、3...遞增的順序給你這些數。是否是很方便的構建一棵樹。而後你能夠自由自在的在這棵樹上玩二分查找。
那假設你自定義了主鍵索引,並且你自定義的這個主鍵索引並不必定是自增的。
那就有可能出現下面這種狀況 以下圖:
假設上圖中的id就是你自定義的不會自增的主鍵
而後隨着你將數據寫入。就致使後一個數據頁中的全部行並不必定比前一個數據頁中的行的id大。
這時就會觸發頁分裂的邏輯。
頁分裂的目的就是保證:後一個數據頁中的全部行主鍵值比前一個數據頁中主鍵值大。
通過分裂調整,能夠獲得下面的這張圖。
參考:
https://dev.mysql.com/doc/refman/5.7/en/glossary.html
面試官都關注了!你還在猶豫什麼呢?