1. 程式人生 > >mysql 聚集索引 非聚集索引 概念梳理

mysql 聚集索引 非聚集索引 概念梳理

聚集索引

  一種索引,該索引中鍵值的邏輯順序決定了表中相應行的物理順序。
  聚集索引確定表中資料的物理順序。聚集索引類似於電話簿,後者按姓氏排列資料。由於聚集索引規定資料在表中的物理儲存順序,因此一個表只能包含一個聚集索引。但該索引可以包含多個列(聯合索引)(不過mysql的innodb只支援主鍵聚集索引,不支援聯合聚集索引),就像電話簿按姓氏和名字進行組織一樣。

非聚集索引

  一種索引,該索引中索引的邏輯順序與磁碟上行的物理儲存順序不同,一個表可以包含多個非聚集索引。

InnoDB索引實現

InnoDB的資料檔案本身就是索引檔案。從上文知道,MyISAM索引檔案和資料檔案是分離的,索引檔案僅儲存資料記錄的地址。而在InnoDB中,表資料檔案本身就是按B+Tree組織的一個索引結構,這棵樹的葉節點data域儲存了完整的資料記錄。這個索引的key是資料表的主鍵,因此InnoDB表資料檔案本身就是主索引。

這裡寫圖片描述

  上圖是InnoDB聚集索引的資料結構示意圖,可以看到葉節點的data域包含了完整的資料記錄。因為InnoDB的資料檔案本身要按主鍵聚集,所以InnoDB要求表必須有主鍵(MyISAM可以沒有),innodb會按照如下規則進行處理:
  1,如果一個主鍵被定義了,那麼這個主鍵就是作為聚集索引
  2,如果沒有主鍵被定義,那麼該表的第一個唯一非空索引被作為聚集索引
  3,如果沒有主鍵也沒有合適的唯一索引,那麼innodb內部會生成一個隱藏的主鍵作為聚集索引,這個隱藏的主鍵是一個6個位元組的列,改列的值會隨著資料的插入自增。

接下來說一說innodb的非聚集索引
  和其他引擎不同的是,innodb的非聚集索引的葉子節點上的data是主鍵(所以聚集索引的key,不能過長)。為什麼存放的主鍵,而不是記錄所在地址呢,理由相當簡單,因為記錄所在地址並不能保證一定不會變,但主鍵可以保證,如下圖:
  
這裡寫圖片描述


圖中第二行為葉子節點,葉子結點的data域,則為主鍵。

  PS:在梳理概念和查閱資料的過程中,發現自己對唯一索引和聚集索引的概念有點混淆,特地查了一下:

  唯一索引是給所做的索引增加了唯一性的約束,新增,修改索引列中資料時,不允許出現重複值.它可以是聚集索引,也可以是非聚集的,就看如何去定義。
  主鍵索引是把主鍵列定義為索引,主鍵具有唯一性,所以主鍵索引是唯一索引的一種特殊形式 。