MySql中B-Tree索引和Hash索引

在MySQL中索引是在存儲引擎層實現的,而不是在服務器層實現的。所以,不一樣的存儲引擎實現也是不一樣的。<br>mysql

B-Tree索引:<br> Innodb引擎使用B+Tree實現<br> MyISAM使用前綴壓縮技術使得索引更小,InnoDb按照原數據格式進行存儲。<br>sql

MyISAM索引經過數據的物理位置引用被索引的行,而InnoDB根據主鍵引用被索引的行。<br>服務器

B-Tree索引可以加快數據的訪問速度,由於存儲引擎不須要全表掃描來獲取須要的數據,而是從索引的根節點開始進行搜索,跟節點的槽中存放了指向子節點的指針,存儲引擎根據指針向下層查找,這些節點定義了子節點的上限和下限;<br>數據結構

B-Tree索引列是順序組織的,因此很適合查找範圍數據,像「找出I到K開頭的名字」,查詢效率很是高。<br>函數

B-Tree索引適用於全值匹配、匹配最左前綴、匹配列前綴、匹配範圍值、精確匹配某一列而且範圍匹配另外一列、只訪問索引的查詢。<br>優化

由於B-Tree索引樹中的節點是有順序的,因此索引還能夠用於order by操做。指針

B-Tree索引的限制:<br>code

  1. 若是不是按照索引的最左列開始查找,則沒法使用索引。<br>
  2. 沒法跳過索引中的列。<br>
  3. 若是查詢中有範圍查詢,其右邊全部的列都沒法使用索引優化查找。例如:<br> where last_name = 'Smith' and first_name like 'J%' and birth = '1990-11-12'只能使用索引的前兩列,第二列中有like是範圍查詢,後邊的列沒法使用索引。

所以,索引列的順序很是重要!!!<br>排序

Hash索引:<br> Hash索引是基於Hash表實現的,只有精確匹配的查找纔能有效。對於每一行數據,存儲引擎對全部的索引列計算一個Hash碼,不一樣的建值計算出來的Hash碼不同,Hash索引將全部的Hash碼存儲在索引中,同時在索引中保存指向每一個數據行的指針。<br> 例如:對fname創建hash索引<br>索引

mysql> select * from testhash;
fname lname
Jack Lentz
Tom James
Kobe Zaitsev
Vadim Tkachenko

假設該索引使用Hash函數f(),返回下面的值<br>

f('Jack') = 2233<br> f('Tom') = 6890<br> f('Kobe') = 5678<br> f('Vadim') = 9881<br>

在Hash槽中有以下數據結構<br>

槽(Slot) 值(value)
2233 第一行數據
5678 第三行數據
6890 第二行數據
9881 第四行數據

在Hash槽是有序存儲的,可是數據行是無序的。<br>

mysql> select lname from testhash where fname = 'Kobe'

MySql存儲引擎先計算Kobe的hash值,而且找到對應記錄的指針,而後找到第三行的值,比較是否爲Kobe,確保就是要查找的行。<br> Hash索引的限制:<br>

Hash索引不是按照索引值的順序存儲的,所以不能用於order by排序。

Hash索引不支持匹配查找。

Hash索引不支持任何的範圍查找。

當出現Hash衝突時,存儲引擎必須遍歷全部行的指針,逐行比較。

索引的優勢:<br>

  1. 大大減小服務器須要掃描的數據量<br>

  2. 幫助服務器避免排序和臨時表的建立<br>

  3. 索引可以把隨機IO變爲順序IO

相關文章
相關標籤/搜索