學習筆記:InnoDB表和索引結構(二)
4、 自適應的雜湊索引
如果一個表幾乎完全快取在主記憶體中,在其上執行查詢最快的方法就是使用雜湊索引。InnoDB有一個自動機制,它監視對為一個表定義的索引的索引搜尋。如果InnoDB注意到查詢會從建立一個雜湊索引中獲益,它會自動地這麼做。
注意,雜湊索引總是基於表上已存在的B樹索引來建立。根據InnoDB對B樹索引觀察的搜尋方式,InnoDB會在為該B樹定義的任何長度的鍵的一個字首上建立雜湊索引。
雜湊索引可以是部分的:它不要求整個B樹索引被快取在緩衝池。InnoDB根據需要對被經常訪問的索引的那些頁面建立雜湊索引。
在某種意義上,InnoDB透過自適應的雜湊索引機制來調整自己,使其更加貼近主記憶體資料庫的架構。
InnoDB表的物理行結構取決於表建立時指定的行格式。在MySQL 5.1中,InnoDB預設使用緊湊(COMPACT)格式,但為
了保留與舊版本MySQL的相容性,冗餘(REDUNDANT)格式也可用。檢視InnoDB表的行格式,可使用SHOW TABLE
STATUS命令。
緊湊的行格式大約可減少20%的儲存空間,但某些操作會增加CPU使用量。如果是一個典型的受限於快取記憶體命中率和
磁碟速度的工作負荷,使用緊湊格式可能會更快。如果是一種少見工作負荷情況,由於有限的CPU速度,緊湊格式可
能會比較慢。
使用冗餘行格式的InnoDB錶行具有以下特點:
- InnoDB中每個索引記錄包含一個6位元組的頭。這個頭被用來將連續的記錄連線在一起,並且也用在row-level鎖定中。
- 聚集索引裡的記錄包含所有的使用者定義列。此外,還有6個位元組的事務ID和一個7個位元組的回滾指標。
- 如果一個表沒有定義主鍵,每個聚集索引記錄還包含一個6位元組的RowID。
- 每個第二索引記錄包含聚集索引鍵定義的所有主鍵列。
- 一個記錄也包含一個指向該記錄每個列的指標,如果在一個記錄中列的總長度小於128位元組,該指標是一個位元組;否則就是2位元組。這些指標的陣列被稱為記錄目錄。這些指標指向的區域被稱為記錄的資料部分。
- 在內部,InnoDB以固定長度格式儲存固定長度的字元列,比如CHAR(10)。InnoDB不截斷VARCHAR列的尾隨空格。
- 一個SQL的NULL值在記錄目錄裡佔1到2位元組。例如,在一個可變長度列,如果存的是SQL的NULL值,則在記錄資料部分佔零位元組。在一個固定長度列,記錄的資料部分佔該列的固定長度。為NULL值保留固定空間的動機是之後該列從NULL值到非NULL值的更新可以就地完成,且不會導致索引頁的碎片。
使用緊湊行格式的InnoDB錶行具有以下特點:
- InnoDB中每個索引記錄包含一個5位元組的頭,在此之前是一個可變長度頭。這個頭被用來將連續的記錄連線在一起,並且也用在row-level鎖定中。
- 在記錄頭的可變長度部分包含一個用來標識NULL列的位向量。如果索引中可為NULL的列的數量為N,則該位向量佔用(N+7)/8個位元組。NULL列完全不佔用這個位向量以外的空間。在頭的可變長度部分也包含可變長列的長度。每個長度需要一個或兩個位元組,這取決於該列的最大長度。如果索引中的所有列都是NOT NULL的並且是固定長度的,記錄頭就沒有可變長度部分。
- 對於每一個非空的可變長欄位,記錄頭用一個或兩個位元組儲存列長度。兩個位元組只用在列的一部分資料外部儲存在溢位頁上或者列最大長度超過255個位元組並且實際長度超過127位元組的情況下。對於外部儲存的列,這兩個位元組長度表示內部儲存部分的長度加上20位元組的外部儲存指標。例如內部儲存部分是768位元組,這個長度就是768+20。20位元組長的指標儲存了列的真實長度。
- 記錄頭後緊跟著的是非空列的資料內容。
- 聚集索引裡的記錄包含所有的使用者定義列。此外,還有6個位元組的事務ID和一個7個位元組的回滾指標。
- 如果一個表沒有定義主鍵,每個聚集索引記錄還包含一個6位元組的RowID。
- 每個第二索引記錄也包含為聚集索引鍵定義的所有主鍵列。如果任何主鍵欄位是可變長的,則每一個第二索引的記錄頭必須有一個可變長部分來記錄這些可變長列的長度,即使第二索引是建立在固定長的列上。
- 在內部,InnoDB以固定長度格式儲存固定長度、固定寬度的字元列,如CHAR(10)。InnoDB不截斷VARCHAR列的尾隨空格。
- 在內部,InnoDB會將UTF-8的CHAR(N)的列儲存在N位元組裡,並截斷尾隨空格。(如果冗餘行格式,這樣的列會佔據3 ×N位元組。 )在許多情況下,保留最低限度的空間N可以保持列在更新時不會造成索引碎片。
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/124805/viewspace-1024340/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- InnoDB學習(七)之索引結構索引
- 《MySQL實戰45講》學習筆記4——MySQL中InnoDB的索引MySql筆記索引
- 架構學習筆記系列二架構筆記
- Redis學習筆記(二)redis 底層資料結構Redis筆記資料結構
- 資料結構 第二章(學習筆記一)資料結構筆記
- 資料結構與演算法-學習筆記(二)資料結構演算法筆記
- GO 學習筆記->結構體Go筆記結構體
- 資料結構學習筆記資料結構筆記
- MySQL提升筆記(4)InnoDB儲存結構MySql筆記
- Vue & Bootstrap 結合學習筆記(二)Vueboot筆記
- ES6學習筆記二(變數結構賦值)筆記變數賦值
- MySQL學習筆記:索引失效MySql筆記索引
- 結構動力學教材-學習筆記筆記
- innodb學習筆記(一) aio的使用筆記AI
- MySQL:Innodb恢復的學習筆記MySql筆記
- Oracle體系結構學習筆記Oracle筆記
- 資料結構學習筆記--棧資料結構筆記
- 資料結構學習筆記1資料結構筆記
- 資料結構和演算法-學習筆記(一)資料結構演算法筆記
- InnoDB學習(八)之 聚簇索引索引
- MySQL學習筆記:組合索引-索引下推MySql筆記索引
- 我的 golang 學習筆記系列三:結構體和介面Golang筆記結構體
- iOS學習筆記44 Swift(四)列舉和結構體iOS筆記Swift結構體
- InnoDB文件筆記(二)—— Redo Log筆記
- 資料結構學習筆記-堆排序資料結構筆記排序
- 結構化程式設計--學習筆記程式設計筆記
- jQuery 學習筆記:jQuery 程式碼結構jQuery筆記
- Java學習筆記:資料結構之線性表(雙向連結串列)Java筆記資料結構
- 關於MySQL InnoDB表的二級索引是否加入主鍵的總結MySql索引
- Docker構建自己的容器(學習筆記二)Docker筆記
- TS學習筆記(二)筆記
- ANFIS學習筆記(二)筆記
- activiti學習筆記二筆記
- Typescript學習筆記(二)TypeScript筆記
- JavaScript學習筆記(二)JavaScript筆記
- Hibernate學習筆記二筆記
- React 學習筆記【二】React筆記
- TensorFlow學習筆記(二)筆記
- vue學習筆記二Vue筆記