聯合索引在B+樹上的結構


 

一級索引

二級聯合索引

假設這是一個多列索引(col1, col2,col3),對於葉子節點,是這樣的: 

PS:該圖改自《MySQL索引背后的數據結構及算法原理》一文的配圖。

也就是說,聯合索引(col1, col2,col3)也是一棵B+Tree,其非葉子節點存儲的是第一個關鍵字的索引,而葉節點存儲的則是三個關鍵字col1、col2、col3三個關鍵字的數據,且按照col1、col2、col3的順序進行排序。

配圖可能不太讓人滿意,因為col1都是不同的,也就是說在col1就已經能確定結果了。自己又畫了一個圖(有點丑),col1表示的是年齡,col2表示的是姓氏,col3表示的是名字。如下圖: 

PS:對應地址指的是數據記錄的地址。

如圖,聯合索引(年齡, 姓氏,名字),葉節點上data域存儲的是三個關鍵字的數據。且是按照年齡、姓氏、名字的順序排列的。

因此,如果執行的是: 
select * from STUDENT where 姓氏='李' and 名字='安'; 
或者 
select * from STUDENT where 名字='安'; 
那么當執行查詢的時候,是無法使用這個聯合索引的。因為聯合索引中是先根據年齡進行排序的。如果年齡沒有先確定,直接對姓氏和名字進行查詢的話,就相當於亂序查詢一樣,因此索引無法生效。因此查詢是全表查詢。

如果執行的是: 
select * from STUDENT where 年齡=1 and 姓氏='李'; 
那么當執行查詢的時候,索引是能生效的,從圖中很直觀的看出,age=1的是第一個葉子節點的前6條記錄,在age=1的前提下,姓氏=’李’的是前3條。因此最終查詢出來的是這三條,從而能獲取到對應記錄的地址。 
如果執行的是: 
select * from STUDENT where 年齡=1 and 姓氏='黃' and 名字='安'; 
那么索引也是生效的。

 

而如果執行的是: 
select * from STUDENT where 年齡=1 and 名字='安'; 
那么,索引年齡部分能生效,名字部分不能生效。也就是說索引部分生效。

因此我對聯合索引結構的理解就是B+Tree是按照第一個關鍵字進行索引,然后在葉子節點上按照第一個關鍵字、第二個關鍵字、第三個關鍵字…進行排序。

最左原則

而之所以會有最左原則,是因為聯合索引的B+Tree是按照第一個關鍵字進行索引排列的。

MySQL InnoDB聚簇及輔助索引


免責聲明!

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



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