MySQL 8.0 新特性之隱藏索引
文章目錄
原文地址:MySQL 8.0 Reference Manual
MySQL 8.0 支援隱藏索引(invisible index),也稱為不可見索引。隱藏索引不會被優化器使用。主鍵不能設定為隱藏(包括顯式設定或隱式設定)。
索引預設是可見的(visible)。使用CREATE TABLE
、CREATE INDEX
或ALTER TABLE
語句的VISIBLE
或者INVISIBLE
選項設定一個新建索引的可見性:
CREATE TABLE t1 (
i INT,
j INT,
k INT,
INDEX i_idx (i) INVISIBLE
) ENGINE = InnoDB;
CREATE INDEX j_idx ON t1 (j) INVISIBLE;
ALTER TABLE t1 ADD INDEX k_idx (k) INVISIBLE;
使用ALTER TABLE ... ALTER INDEX
語句的VISIBLE
或者INVISIBLE
選項修改已有索引的可見性:
ALTER TABLE t1 ALTER INDEX i_idx INVISIBLE;
ALTER TABLE t1 ALTER INDEX i_idx VISIBLE;
通過資料字典表 INFORMATION_SCHEMA.STATISTICS 或者SHOW INDEX
mysql> SELECT INDEX_NAME, IS_VISIBLE
FROM INFORMATION_SCHEMA.STATISTICS
WHERE TABLE_SCHEMA = 'db1' AND TABLE_NAME = 't1';
+------------+------------+
| INDEX_NAME | IS_VISIBLE |
+------------+------------+
| i_idx | YES |
| j_idx | NO |
| k_idx | NO |
+------------+------------+
不可見索引特性可以用於測試刪除某個索引對於查詢效能的影響,同時又不需要真正刪除索引,也就避免了錯誤刪除之後的索引重建。對於一個大表上的索引進行刪除重建將會非常耗時,而將其設定為不可見或可見將會非常簡單快捷。
如果某個設定為隱藏的索引實際上仍然需要或者被優化器所使用,可以通過以下多種方法發現缺少該索引帶來的影響:
- 索引提示中使用了該索引的查詢將會產生錯誤。
- 效能模式(Performance Schema)中的資料顯示受影響查詢的負載升高。
- EXPLAIN 語句顯示了不同的查詢執行計劃。
- 慢查詢日誌中出現了新的查詢語句。
系統變數 optimizer_switch 的 use_invisible_indexes 值控制了優化器構建執行計劃時是否使用隱藏索引。如果設定為 off (預設值),優化器將會忽略隱藏索引(與引入該屬性之前的行為相同)。如果設定為 on,隱藏索引仍然不可見,但是優化器在構建執行計劃時將會考慮這些索引。
索引的可見性不會影響索引的維護。例如,無論索引是否可見,每次修改表中的資料時都需要對相應索引進行更新,而且唯一索引都會阻止插入重複的列值。
一個沒有明確定義主鍵的表仍然可能存在有效的隱式主鍵( 表中某些 NOT NULL 欄位上建立了 UNIQUE 索引)。在這種情況下,表中第一個這樣的索引和顯式主鍵存在相同的約束效果,該索引也不能被設定為不可見。假如存在以下表定義:
CREATE TABLE t2 (
i INT NOT NULL,
j INT NOT NULL,
UNIQUE j_idx (j)
) ENGINE = InnoDB;
定義中沒有明確指定主鍵,但是 NOT NULL 欄位 j 上存在一個唯一索引,它實現了和主鍵相同的資料約束,不能設定為不可見:
mysql> ALTER TABLE t2 ALTER INDEX j_idx INVISIBLE;
ERROR 3522 (HY000): A primary key index cannot be invisible.
如果為該表指定一個顯式的主鍵:
ALTER TABLE t2 ADD PRIMARY KEY (i);
該主鍵不能設定為不可見。除此之外,欄位 j 上的唯一索引不再是一個隱式的主鍵,因此可以設定為隱藏索引:
mysql> ALTER TABLE t2 ALTER INDEX j_idx INVISIBLE;
Query OK, 0 rows affected (0.03 sec)
隱藏索引應用場景:軟刪除、灰度釋出。
歡迎留言討論!