MySQL 8+
InnoDB
-
序章
索引失效,發生在 已經建立索引,但是,查詢(SELECT)時沒有用到建立的(預期會用到)索引的情況下。
失效原因有兩個方面:
1、建立索引的方式錯誤
需要弄清楚 欄位的 #區分度(極其重要) 這個概念。選擇 區分度高 的建立索引。
2、某些SELECT語句不支援 使用索引
注意,除了索引失效,導致 慢查詢 的另一個重要原因是——沒有建立索引,沒有在 建立表 的時候第一時間建立索引。
本文探索 MySQL使用時常見的索引失效情況,做個彙總。
通義千問
問題:InnoDB:索引失效會在什麼情況下發生?
回答:
在 InnoDB 儲存引擎中,索引失效 是指 查詢最佳化器 決定不使用已存在的索引,而是 選擇全表掃描 或 其他方式來執行查詢。
以下是一些常見的索引失效情況:
1)選擇性低的索引
原因:如果索引的選擇性很低(即索引列的重複值很多),MySQL 可能會選擇不使用該索引,因為全表掃描可能更快。
#區分度
2)使用 OR 運算子
原因:當查詢條件中包含 OR 運算子時,如果 OR 連線的條件不能使用同一個索引,MySQL 可能會選擇不使用索引。
3)使用函式或表示式
原因:在索引列上使用函式或表示式會導致索引失效,因為 MySQL 無法直接使用索引進行查詢。
4)使用 LIKE 模糊查詢
原因:如果 LIKE 模糊查詢的字首是萬用字元(如 %),索引將失效。
5)資料型別不匹配
原因:如果查詢條件中的資料型別與索引列的資料型別不匹配,MySQL 可能會選擇不使用索引。
6)使用 NOT 運算子
原因:使用 NOT 運算子(如 != 或 <>)時,MySQL 可能會選擇不使用索引,因為這些運算子通常會導致全表掃描。
7)使用 IN 運算子
原因:如果 IN 運算子中的值列表非常大,MySQL 可能會選擇不使用索引。
8)索引列上有大量 NULL 值
原因:如果索引列中有大量 NULL 值,MySQL 可能會選擇不使用該索引。
9)複合索引的使用不當
原因:如果複合索引的前導列沒有出現在查詢條件中,MySQL 可能會選擇不使用該複合索引。
10)表統計資訊不準確
原因:如果表的統計資訊不準確,MySQL 的查詢最佳化器可能會做出錯誤的決策,導致索引失效。
11)使用 LIMIT 時
原因:在某些情況下,使用 LIMIT 時,MySQL 可能會選擇不使用索引,特別是當 LIMIT 的偏移量很大時。
12)使用 JOIN 時
原因:在複雜的 JOIN 查詢中,如果 JOIN 條件不使用索引,MySQL 可能會選擇不使用索引。
解決方法
1、最佳化查詢條件:確保查詢條件儘可能精確,避免使用函式、表示式和萬用字元。 2、使用合適的索引:為查詢條件中的列建立合適的索引,特別是複合索引。 3、定期更新統計資訊:使用 ANALYZE TABLE 命令定期更新表的統計資訊。 4、避免使用 SELECT *:只選擇需要的列,減少資料傳輸量。 5、使用 EXPLAIN 分析查詢:使用 EXPLAIN 命令分析查詢計劃,確保索引被正確使用。 |
注,大家可以自行去提問。
參考資料#2
補充了2條:
13)資料表過度索引:太多
文中提到,索引太多,可能導致 查詢最佳化器 選擇錯亂。
14)資料表過度龐大
文中提到,資料表太大時,索引的效果減弱了。
文中提到,可以使用 分割槽(PARTITION BY)、分片(ShardingSphere 等工具) 解決該問題。
或許,還有 分庫,還有 使用 其它大資料儲存工具。
小結
基本的 索引失效 大概就這些了,足夠平時開發使用了。
進一步探索:TODO
1、分割槽、分表、分庫 的索引如何建立?
2、MySQL 的 一些叢集方案中怎麼建立索引?這涉及到 大資料方面使用 MySQL 了吧?不太懂。
---END---
本文連結:
https://www.cnblogs.com/luo630/p/18448905
參考資料
1、通義千問
2、MySQL索引失效及避免策略:最佳化查詢效能的關鍵
作者:糜終
2024-09-30
https://developer.aliyun.com/article/1615655
3、
ben釋出於部落格園
ben釋出於部落格園