日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > 数据库 >内容正文

数据库

MySQL优化(二):索引的类型、匹配原则、创建原则

發布時間:2023/12/3 数据库 31 豆豆
生活随笔 收集整理的這篇文章主要介紹了 MySQL优化(二):索引的类型、匹配原则、创建原则 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

目錄

    • 索引的優缺點
    • 索引類型
      • 聚簇索引(主鍵索引)
      • 非聚簇索引(二級索引、輔助索引)
    • 索引匹配的原則
      • 最左匹配原則
    • 無法使用索引的場景
    • 索引創建的原則
    • 使不使用索引的依據到底是什么?
    • 參考

索引的優缺點

常見的索引結構有: B 樹, B+樹和 Hash。

  • 優點:加快數據的檢索速度
  • 缺點:
  • 創建索引和維護索引需要耗費許多時間:當對表中的數據進行增刪改的時候,如果數據有索引,那么索引也需要動態的修改,會降低 SQL 執行效率。
  • 占用物理存儲空間 :索引需要使用物理文件存儲,也會耗費一定空間。

索引類型

聚簇索引(主鍵索引)

聚簇索引即索引結構和數據一起存放的索引,結構為B+樹。
InnoDB中,表數據文件本身就是按B+Tree組織的一個索引結構,聚簇索引就是按照每張表的主鍵構造一顆B+樹,同時葉子節點中存放的就是整張表的行記錄數據,也將聚集索引的葉子節點稱為數據頁。

聚簇索引結構如下:

非聚簇索引(二級索引、輔助索引)

在聚簇索引之上創建的索引稱之為輔助索引(二次索引),輔助索引節點只包含索引列值和主鍵值,因此輔助索引訪問數據總是需要二次查找(即:通過二次索引找到主鍵值后回到聚簇索引找到對應的數據行)。
輔助索引葉子節點存儲的不再是行的物理位置,而是主鍵值。通過輔助索引首先找到的是主鍵值,再通過主鍵值找到數據行的數據頁,再通過數據頁中的Page Directory找到數據行。
Innodb輔助索引非葉子節點只有索引列(不含主鍵),葉子節點并不包含行記錄的全部數據,葉子節點只包含索引列和相應行數據的聚簇索引鍵。

Innodb二級索引,索引列值全相同的情況下,節點按主鍵值排序。

二級索引結構如下:

索引匹配的原則

最左匹配原則

如果創建一個聯合索引, 此索引的任何前綴都會用于查詢, 例如:
(col1, col2, col3)這個聯合索引的所有前綴就是(col1), (col1, col2), (col1, col2, col3), 包含這些列的查詢都會啟用索引查詢.
其他所有不在最左前綴里的列都不會啟用索引, 即使包含了聯合索引里的部分列也不會使用索引. 即上述中的(col2), (col3), (col2, col3) 都不會啟用索引去查詢.
注意:(col1, col3)會啟用(col1)的索引查詢。

無法使用索引的場景

  • 復合索引的情況下,查詢條件不滿足索引最左的原則
  • Mysql估計使用索引比全表掃描慢
  • 索引 不能是表達式(函數)的一部分
    只有獨立的列能使用索引,如:SELECT * FROM table WHERE id -1 = 1000; 無法使用索引 因為索引 id-1 不為獨立的列
  • 負向查詢(not , not in, not like, <>, != ,!>,!< ) 不會使用索引
  • 以%開頭的LIKE查詢不能夠利用B-tree索引
  • 用or分割開的條件,or前條件有索引,or后的列沒有索引

    因為or后面的條件沒有索引,那么后面的查詢肯定要進行全表掃描,在存在全表掃描的情況下,就沒有必要多一次索引掃描增加IO訪問。

  • 索引創建的原則

    • 不要使用更新頻繁的列作為主鍵,不適用多列主鍵(相當于聯合索引)
    • 不要使用 UUID,MD5,HASH,字符串列作為主鍵(無法保證數據的順序增長),容易導致頁分裂及隨機IO,影響插入的速度。推薦使用自增值作為主鍵。
    • 索引列的順序:
    • 區分度最高的放在聯合索引的最左側(區分度=列中不同值的數量/列的總行數)
    • 盡量把字段長度小的列放在聯合索引的最左側(因為字段長度越小,一頁能存儲的數據量越大,IO 性能也就越好)
    • 使用最頻繁的列放到聯合索引的左側(這樣可以比較少的建立一些索引)
    • 避免建立冗余索引和重復索引(增加了查詢優化器生成執行計劃的時間)
      冗余索引示例:index(a,b,c)、index(a,b)、index(a)
    • 對于頻繁的查詢優先考慮使用覆蓋索引

    覆蓋索引:就是包含了所有查詢字段 (where,select,ordery by,group by 包含的字段) 的索引
    覆蓋索引的好處:
    避免 Innodb 表進行索引的二次查詢: Innodb 是以聚集索引的順序來存儲的,對于 Innodb 來說,二級索引在葉子節點中所保存的是行的主鍵信息,如果是用二級索引查詢數據的話,在查找到相應的鍵值后,還要通過主鍵進行二次查詢才能獲取我們真實所需要的數據。而在覆蓋索引中,二級索引的鍵值中可以獲取所有的數據,避免了對主鍵的二次查詢 ,減少了 IO 操作,提升了查詢效率。
    可以把隨機 IO 變成順序 IO 加快查詢效率: 由于覆蓋索引是按鍵值的順序存儲的,對于 IO 密集型的范圍查找來說,對比隨機從磁盤讀取每一行的數據 IO 要少的多,因此利用覆蓋索引在訪問時也可以把磁盤的隨機讀取的 IO 轉變成索引查找的順序 IO。

    使不使用索引的依據到底是什么?

    在滿足了使用索引的條件下,是否使用索引取決于使用索引的成本。

    此段摘抄自:MySQL中IS NULL、IS NOT NULL、!=不能用索引?胡扯!

    MySQL中決定使不使用某個索引執行查詢的依據很簡單:就是成本夠不夠小。而不是是否在WHERE子句中用了IS NULL、IS NOT NULL、!=這些條件。

    答案很簡單:成本。對于使用二級索引進行查詢來說,成本組成主要有兩個方面:
    1. 讀取二級索引記錄的成本
    2. 將二級索引記錄執行回表操作,也就是到聚簇索引中找到完整的用戶記錄的操作所付出的成本。

    查詢列不在二級索引時,要掃描的二級索引記錄條數越多,那么需要執行的回表操作的次數也就越多,達到了某個比例時,使用二級索引執行查詢的成本也就超過了全表掃描的成本(舉一個極端的例子,比方說要掃描的全部的二級索引記錄,那就要對每條記錄執行一遍回表操作,自然不如直接掃描聚簇索引來的快)。

    參考

    • 什么是索引?
    • 官方文檔解釋MySQL最左匹配(最左前綴)原則
    • MySQL中IS NULL、IS NOT NULL、!=不能用索引?胡扯!
    • MySQL優化指南
    • mysql 存在索引但不能使用索引的典型場景
    • 聚簇索引和非聚簇索引(通俗易懂 言簡意賅)

    總結

    以上是生活随笔為你收集整理的MySQL优化(二):索引的类型、匹配原则、创建原则的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。