首頁 >資料庫 >mysql教程 >給Myql建立索引

給Myql建立索引

亚连
亚连原創
2018-05-10 10:10:101487瀏覽

為了提升Mysql的效能我們可以建立索引,來提升Mysql的搜尋速度,還可以緩解對Mysql資料庫的壓力,下面我們來談談關於Mysql的索引和一些進階用法。

所有MySQL欄位類型可以被索引。根據儲存引擎定義每個資料表的最大索引數和最大索引長度。
所有儲存引擎支援每個表至少16個索引,總索引長度至少為256位元組。大多數儲存引擎有更高的限制。

#的儲存類型目前只有兩種(btree和hash),特定和儲存引擎模式相關:
MyISAM        btree
InnoDB        btree
#MEMORY/Heap   hash,btree

預設MEMORY/Heap儲存引擎使用hash索引


MySQL的btree索引和hash索引的差異
hash 索引結構的特殊性,其檢索效率非常高,索引的檢索可以一次定位,不像btree(B- Tree)索引需要從根節點到枝節點,最後才能訪問到頁節點這樣多次的IO訪問,所以hash 索引的查詢效率要遠高於btree(B-Tree) 索引。

雖然 hash 索引效率高,但是 hash 索引本身由於其特殊性也帶來了很多限制和弊端,主要有以下這些。
(1)hash 索引只要能滿足=,<=>,IN,IS NULL或IS NOT NULL查詢,不能使用範圍查詢。
由於hash 索引比較的是進行hash 運算之後的hash 值,所以它只能用於等值的過濾,不能用於基於範圍的過濾,因為經過對應的hash 演算法處理之後的hash 值的大小關係,並不能保證和hash運算前完全一樣。

(2)hash 索引無法被用來避免資料的排序運算。
由於hash 索引中存放的是經過hash 計算之後的hash 值,而且hash值的大小關係並不一定和hash 運算前的鍵值完全一樣,所以資料庫無法利用索引的資料來避免任何排序運算;

(3)hash 索引不能利用部分索引鍵查詢。
對於組合索引,hash 索引在計算hash 值的時候是組合索引鍵合併後再一起計算hash 值,而不是單獨計算hash 值,所以透過組合索引的前面一個或幾個索引鍵進行查詢的時候,hash 索引也無法被利用。

(4)hash 索引在任何時候都無法避免表格掃描。
前面已經知道,hash 索引是將索引鍵通過hash 運算之後,將hash運算結果的hash 值和對應的行指標資訊存放於一個hash 表中,由於不同索引鍵存在相同hash 值,所以即使取滿足某個hash 鍵值的資料的記錄條數,也無法從hash 索引中直接完成查詢,還是要透過存取表中的實際資料進行對應的比較,並得到對應的結果。

(5)hash 索引遇到大量hash值相等的情況後效能並不一定就會比B-Tree索引高。
對於選擇性比較低的索引鍵,如果建立 hash 索引,那麼將會存在大量記錄指標資訊存於同一個 hash 值相關聯。這樣要定位某一筆記錄時就會非常麻煩,會浪費多次表資料的訪問​​,而造成整體效能低


B-Tree 索引是MySQL 資料庫中使用最為頻繁的索引類型,除了Archive 儲存引擎之外的其他所有的儲存引擎都支援B-Tree 索引。不只在MySQL 中是如此,實際上在其他的許多資料庫管理系統中B-Tree 索引也同樣是作為最主要的索引類型,這主要是因為B-Tree 索引的儲存結構在資料庫的資料檢索中有非常優異的表現。
   一般來說, MySQL 中的B-Tree 索引的實體檔案大多都是以Balance Tree 的結構來儲存的,也就是所有實際需要的資料都存放於Tree 的Leaf Node ,而且到任何一個Leaf Node的最短路徑的長度都是完全相同的,所以我們大家都稱之為B-Tree 索引當然,可能各種資料庫(或MySQL 的各種儲存引擎)在存放自己的B-Tree 索引的時候會對存儲結構稍作改造。
如Innodb 儲存引擎的B-Tree 索引實際使用的儲存結構其實是B Tree ,也就是在B-Tree 資料結構的基礎上做了很小的改造,在每一個Leaf Node 上面出了存放索引鍵的相關資訊之外,還儲存了指向與該Leaf Node 相鄰的後一個LeafNode 的指標訊息,這主要是為了加快檢索多個相鄰Leaf Node 的效率考慮。
   在Innodb 儲存引擎中,有兩種​​不同形式的索引,一種是Cluster 形式的主鍵索引( Primary Key ),另一種則是和其他儲存引擎(如MyISAM 儲存引擎)存放形式基本上相同的普通B-Tree 索引,這種索引在Innodb 儲存引擎中稱為Secondary Index 。
   在Innodb 中如果透過主鍵來存取資料效率是非常高的,而如果是透過Secondary Index 來存取資料的話, Innodb 首先透過Secondary Index 的相關信息,透過對應的索引鍵檢索到Leaf Node之後,需要再透過Leaf Node 中存放的主鍵值再透過主鍵索引來取得對應的資料行。
MyISAM 儲存引擎的主鍵索引和非主鍵索引差異很小,只不過是主鍵索引的索引鍵是一個唯一且非空 的鍵而已。而且MyISAM 儲存引擎的索引和Innodb 的Secondary Index 的儲存結構也基本上相同,主要的區別只是MyISAM 儲存引擎在Leaf Nodes 上面出了存放索引鍵資訊之外,
再存放能直接定位到MyISAM 資料文件中對應的資料行的資訊(如Row Number ),但不會存放主鍵的鍵值資訊。

索引分單列索引和組合索引。單列索引,即一個索引只包含單一資料列,一個表格可以有多個單列索引,但這不是組合索引。組合索引,即一個索包含​​多個列。
MySQL索引類型包括:
(1)普通索引,這是最基本的索引,它沒有任何限制。它有以下幾個建立方式:

-- 建立索引

CREATE INDEX indexName ON mytable(username(10));               --單一列索引

-- CREATE INDEX indexName ON mytable(username(10),city(10));   -- 組合索引

-- indexName為索引名,mytable表名,username和city為列名,10為前綴長度,即索引在該列從最左字元開始儲存的資訊長度,單位位元組

-- 如果是CHAR,VARCHAR類型,前綴長度可以小於欄位實際長度;如果是BLOB和TEXT類型,必須指定前綴長度,則下同。

-- 修改表結構來建立索引

ALTER TABLE mytable ADD INDEX indexName (username(10));

-- ALTER TABLE mytable ADD INDEX indexName (username(10),city(10));

-- 此處indexName 索引名稱可不寫,系統自動賦名username ,username_2 ,username_3,...

# -- 建立表格的時候直接指定

CREATE TABLE mytable(

id ​​INT,

username VARCHAR(16),

city VARCHAR(16),

age INT,

INDEX indexName (username(10))-- INDEX indexName (username(10),city(10))

);

-- 此處indexName 索引名同樣可以省略

(2)唯一索引,它與前面的普通索引類似,不同的就是:索引列的值必須唯一,但允許有空值。如果是組合索引,則列值的組合必須唯一。它有以下幾種建立方式(僅在建立普通索引時關鍵字INDEX 前加UNIQUE):

#-- 建立索引

CREATE UNIQUE INDEX indexName ON mytable(username(10));

-- 修改表結構來建立索引

ALTER TABLE mytable ADD UNIQUE INDEX indexName (username(10 ));-- 也可簡寫成ALTER TABLE mytable ADD UNIQUE indexName (username(10));

-- 建立表格的時候直接指定

#CREATE TABLE mytable(

id ​​INT,

username VARCHAR(16),

city VARCHAR(16),

age INT,

UNIQUE INDEX indexName (username(10)) -- 也可簡單寫成UNIQUE indexName (username(10))

);

(3)主鍵索引,它是一種特殊的唯一索引,不允許有空值。在建表的時候同時建立的主鍵即為主鍵索引
主鍵索引無需命名,一個表只能有一個主鍵。主鍵索引同時可是唯一索引或全文索引,但唯一索引或全文索引不能共存在同一索引:

-- 修改表結構來建立索引ALTER TABLE mytable ADD PRIMARY KEY (id );

-- 建立表格的時候直接指定CREATE TABLE mytable(
id ​​INT,
username VARCHAR(16),
city VARCHAR(16),
age INT, PRIMARY KEY(id)
);

(4)全文索引,InnoDB儲存引擎不支援全文索引:

--建立索引CREATE FULLTEXT INDEX indexName ON mytable(username(10));

-- 修改表結構來建立索引ALTER TABLE mytable ADD FULLTEXT INDEX indexName (username(10));

- - 也可簡寫成ALTER TABLE mytable ADD FULLTEXT indexName (username(10));

-- 建立表的時候直接指定CREATE TABLE mytable(
id ​​INT,
username VARCHAR(16) ,
city VARCHAR(16),
age INT,
FULLTEXT INDEX indexName (username(10))

 -- 也可簡寫成FULLTEXT indexName (username(10)))ENGINE =MYISAM;

-- 建表時建立全文索引,要設定此表的儲存引擎為MYISAM,新版mysql預設InnoDB儲存引擎不支援全文索引

-- 刪除索引DROP INDEX indexName ON mytable;

雖然索引大大提高了查詢速度,同時卻會降低更新表的速度,如對錶進行INSERT、UPDATE和DELETE。因為更新表時,MySQL不僅要保存數據,還要保存索引檔。
建立索引會佔用磁碟空間的索引檔。一般情況這個問題不太嚴重,但如果你在一個大表上建立了多種組合索引,索引檔案的會膨脹很快。

以上是我對Mysql的創建索引總結出來的東西,希望今後會對大家有幫助。

相關文章:

PHP中安插資料到myql顯示亂碼

myql5.7.7最佳化設定參數_MySQL

以上是給Myql建立索引的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn