標籤:tab app 排序 時間複雜度 重複資料 個數 mysq 類型 單表查詢
其實sql最佳化就是對索引的最佳化,不加索引的情況下,單表查詢你怎麼查時間複雜度都是O(n),所以sql最佳化問題關鍵就在索引上。
mysql索引有兩種類型,hash和tree,但是hash的局限性太多了,而且重複資料多時hash索引的效率下降的很快,所以就說一下我對最常用的btree索引的看法。
mysql的btree索引或者叫b+tree索引就是一顆二叉搜尋樹,並且在二叉搜尋樹分葉節點間加了指標以方便排序或查詢某範圍的資料等情況使用。
索引最大的問題就是在很多時候不能生效,網上跟索引有關的文章很多,基本上就是某某情況下索引不能生效,等等一大篇;
但是作為一個程式員如果死記硬背這些個那真沒有用,找個文科生比咱們背的好。所以我總結了幾點索引不能生效的原因,網上說的那些個都可以歸到這幾類裡面。
1,sql寫的不規範或者叫mysql查詢引擎沒有進行最佳化導致不能使索引生效。
舉個例子,如果對某個varchar類型的欄位建立了索引,而我在sql中條件寫的是columnvlaue = 1(注意這是一個數字),這個時候欄位類型和參數類型不符,因此在查詢時索引不會生效。
其實查詢引擎完全可以進行最佳化,或者編寫sql的人完全可以將sql改的規範來避免這個問題。
2,mysql設計的btree不能支援如此查詢。
舉個例子,網上對於like查詢有兩種言論,一種是使用like查詢索引不能生效,一種是使用like進行非最左首碼的查詢索引不能生效;
當然,後者是正確的。mysql的btree索引只支援最左首碼匹配。但是你說它能設計為全部匹配麼,當然可以,比如使用kmp演算法進行子字串匹配。
但是我估計mysql的設計人員實在不想再增加btree索引設計的複雜程度了,或者怕降低查詢的效率(設子字串長度為m,大字串長度為n,匹配的時間複雜度會從O(M)變為O(n+m))。
3,btree根本不支援此種查詢。
比如,反向查詢。你說我的條件是哪個欄位不等於xx,你把這個條件放到二叉搜尋樹裡面去搜尋,它根本就不知道你想要查的資料在哪個子樹上面。
因此就算使用索引,複雜度最壞的情況下也是O(n),跟不使用根本沒區別,所以這種情況也不會使用索引。
以上就是單表情況下索引不能生效的原因分析。
此外還有彙總索引以及多表聯查時索引的使用。彙總索引mysql的處理很簡單,
就是將幾個欄位拼到一起合為一個欄位進行索引,因此索引中的第一個欄位很重要,如果查詢條件中沒有第一個欄位,
彙總索引是不能生效的。至於多表聯查,其實最應該解決的是涉及到的資料數量,這個等我研究透徹了再說吧。
mysql的索引問題分析