<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
《MySQL技術內幕 InnoDB儲存引擎》學習筆記
聚集索引就是按照每張表的主鍵構造一棵B+樹,同時葉子節點中存放的即為整張表的行記錄資料。
舉個例子,直觀感受下聚集索引。
建立表t,並以人為的方式讓每個頁只能存放兩個行記錄(不清楚怎麼人為控制每頁只存放兩個行記錄):
最後《MySQL技術內幕》的作者通過分析工具得到這棵聚集索引樹的大致構造如下:
聚集索引的葉子節點稱為資料頁,每個資料頁通過一個雙向連結串列來進行連結,而且資料頁按照主鍵的順序進行排列。
如圖所示,每個資料頁上存放的是完整的行記錄,而在非資料頁的索引頁中,存放的僅僅是鍵值及指向資料頁的偏移量,而不是一個完整的行記錄。
如果定義了主鍵,InnoDB會自動使用主鍵來建立聚集索引。如果沒有定義主鍵,InnoDB會選擇一個唯一的非空索引代替主鍵。如果沒有唯一的非空索引,InnoDB會隱式定義一個主鍵來作為聚集索引。
輔助索引,也叫非聚集索引。和聚集索引相比,葉子節點中並不包含行記錄的全部資料。葉子節點除了包含鍵值以外,每個葉子節點的索引行還包含了一個書籤(bookmark),該書籤用來告訴InnoDB哪裡可以找到與索引相對應的行資料。
還是以《MySQL技術內幕》中的例子,來直觀感受下輔助索引的模樣。
還是以上面的表t為例,在列c上建立非聚集索引:
然後作者通過分析工作得到輔助索引和聚集索引的關係圖:
可以看到輔助索引idx_c的葉子節點中包含了列c的值和主鍵的值。
以Key為7fffffff為例,7是0111,0代表負數,真實的值應該取反加1,是-1,這是列c的值。Pointer是80000001,8是1000,1代表正數,所以80000001代表1,是主鍵的值。
InnoDB儲存引擎支援覆蓋索引,即從輔助索引中就可以得到查詢的記錄,而不需要查詢聚集索引中的記錄。
使用覆蓋索引有啥好處?
上圖中我們知道,如果要查詢輔助索引中不含有的欄位,得先遍歷輔助索引,再遍歷聚集索引,而如果要查詢的欄位值在輔助索引上就有,就不用再查聚集索引了,這顯然會減少IO操作。
比如上圖中,以下sql可以直接使用輔助索引,
select a from where c = -2;
假設存在如下表:
CREATE TABLE `student` ( `id` bigint(20) NOT NULL, `name` varchar(255) NOT NULL, `age` varchar(255) NOT NULL, `school` varchar(255) NOT NULL, PRIMARY KEY (`id`), KEY `idx_name` (`name`), KEY `idx_school_age` (`school`,`age`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8;
如果在該表上執行:
select count(*) from student
優化器會怎麼處理?
遍歷聚集索引和輔助索引都可以統計出結果,但輔助索引要遠小於聚集索引,所以優化器會選擇輔助索引來統計。執行explain命令:
key和Extra顯示使用了idx_name這個輔助索引。
還有,假設執行以下sql:
select * from student where age > 10 and age < 15
因為聯合索引idx_school_age的欄位順序是先school再age,按照age做條件查詢,通常不走索引:
但是,如果保持條件不變,查詢所有欄位改為查詢條目數:
select count(*) from student where age > 10 and age < 15
優化器會選擇這個聯合索引:
聯合索引是指對錶上的多個列進行索引。
以下為建立聯合索引idx_a_b的範例:
聯合索引的內部結構:
聯合索引也是一棵B+樹,其鍵值數量大於等於2。鍵值都是排序的,通過葉子節點可以邏輯上順序的讀出所有資料。資料(1,1)(1,2)(2,1)(2,4)(3,1)(3,2)是按照(a,b)先比較a再比較b的順序排列。
基於上面的結構,對於以下查詢顯然是可以使用(a,b)這個聯合索引的:
select * from table where a=xxx and b=xxx ; select * from table where a=xxx;
但是對於下面的sql是不能使用這個聯合索引的,因為葉子節點的b值,1,2,1,4,1,2顯然不是排序的。
select * from table where b=xxx
聯合索引的第二個好處是對第二個鍵值已經做了排序。舉個例子:
create table buy_log( userid int not null, buy_date DATE )ENGINE=InnoDB; insert into buy_log values(1, '2009-01-01'); insert into buy_log values(2, '2009-02-01'); alter table buy_log add key(userid); alter table buy_log add key(userid, buy_date);
當執行
select * from buy_log where user_id = 2;
時,優化器會選擇key(userid);但是當執行以下sql:
select * from buy_log where user_id = 2 order by buy_date desc;
時,優化器會選擇key(userid, buy_date),因為buy_date是在userid排序的基礎上做的排序。
如果把key(userid,buy_date)刪除掉,再執行:
select * from buy_log where user_id = 2 order by buy_date desc;
優化器會選擇key(userid),但是對查詢出來的結果會進行一次filesort,即按照buy_date重新排下序。所以聯合索引的好處在於可以避免filesort排序。
到此這篇關於mysql聚集索引、輔助索引、覆蓋索引、聯合索引的使用的文章就介紹到這了,更多相關聚集索引、輔助索引、覆蓋索引、聯合索引內容請搜尋it145.com以前的文章或繼續瀏覽下面的相關文章希望大家以後多多支援it145.com!
相關文章
<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
综合看Anker超能充系列的性价比很高,并且与不仅和iPhone12/苹果<em>Mac</em>Book很配,而且适合多设备充电需求的日常使用或差旅场景,不管是安卓还是Switch同样也能用得上它,希望这次分享能给准备购入充电器的小伙伴们有所
2021-06-01 09:31:42
除了L4WUDU与吴亦凡已经多次共事,成为了明面上的厂牌成员,吴亦凡还曾带领20XXCLUB全队参加2020年的一场音乐节,这也是20XXCLUB首次全员合照,王嗣尧Turbo、陈彦希Regi、<em>Mac</em> Ova Seas、林渝植等人全部出场。然而让
2021-06-01 09:31:34
目前应用IPFS的机构:1 谷歌<em>浏览器</em>支持IPFS分布式协议 2 万维网 (历史档案博物馆)数据库 3 火狐<em>浏览器</em>支持 IPFS分布式协议 4 EOS 等数字货币数据存储 5 美国国会图书馆,历史资料永久保存在 IPFS 6 加
2021-06-01 09:31:24
开拓者的车机是兼容苹果和<em>安卓</em>,虽然我不怎么用,但确实兼顾了我家人的很多需求:副驾的门板还配有解锁开关,有的时候老婆开车,下车的时候偶尔会忘记解锁,我在副驾驶可以自己开门:第二排设计很好,不仅配置了一个很大的
2021-06-01 09:30:48
不仅是<em>安卓</em>手机,苹果手机的降价力度也是前所未有了,iPhone12也“跳水价”了,发布价是6799元,如今已经跌至5308元,降价幅度超过1400元,最新定价确认了。iPhone12是苹果首款5G手机,同时也是全球首款5nm芯片的智能机,它
2021-06-01 09:30:45