2015-07-20 87 views
2

可以像使用普通索引一樣使用mysql前綴索引嗎?Mysql:前綴索引與索引

如果有一些TEXT柱和前綴索引上它是例如長度1,查詢是:

SELECT * FROM table WHERE textcol = 'ab'

難道只是給我的所有行以「a」或它會檢查整個列值?

總的來說,我很好奇,想知道是否使用前綴索引時有什麼注意事項。不涉及性能,如果有任何查詢需要以不同的方式寫入,或者客戶端是否必須執行額外的邏輯,則更多。

回答

3

如果你想一下,MySQL仍然會給你正確的答案,即使沒有索引......它只是不會一樣快......所以,你仍然會用前綴索引得到正確答案。

性能會降低,因爲在將「可能」行與索引匹配之後,服務器將轉到行數據,並根據WHERE子句進一步過濾結果。兩個步驟,而不是一個,但應用程序不需要關心。

的注意事項包括前綴索引不會被優化用於一些操作,如排序或分組,因爲它不包括足夠爲這些目的列數據的事實。

前綴索引未排序超出前綴的長度。如果您的查詢使用完整索引來查找行,則您會經常發現行按照索引順序隱式返回。如果你的應用程序期望這種行爲,那麼它當然期待着它不應該期望的事情,因爲除非你明確地指出ORDER BY,否則行的返回順序是未定義的。在任何查詢中,不要依賴巧合的行爲,因爲不僅前綴索引匹配的行不一定會按照任何特定的順序進行......但事實上,排序不明確的任何結果集的順序都是主題隨時更改。

並且,前綴索引不能被用作覆蓋索引。覆蓋索引指的是SELECT中的所有列碰巧被包括在一個索引中(可選地,主鍵,因爲它總是存在)的情況。優化器將直接從索引中讀取數據,而不是使用索引來標識要在主表數據中查找的行。即使索引不能用於查找匹配的行,優化程序也會僅對覆蓋索引進行全面掃描,而不是對整個表進行全面掃描,從而節省I/O和時間。 (順便提一句,這個功能應該有足夠的理由來選擇你想要的列,而不是懶惰的SELECT * - 它可能會打開一些更有效的查詢計劃)。前綴索引也不能用於此。

但是,除了性能和優化和查詢,隱式做你期望的事情(你不應該期待),沒有注意到與注意前綴索引警告。結果仍然是正確的。

+1

前綴索引不能用於排序的說明,即使前綴長於實際存儲在列中的最長值時,也是在我對相關問題的回答中:http://dba.stackexchange.com/a /11651分之48104。 –

2

通常,「前綴索引」是無用的。我曾經看到過當它認爲可以使用前綴索引時忽略前綴索引的情況。

如果您TEXT場從未超過255個字符更大,將其更改爲VARCHAR(255)(或更小);然後使用一個真正的索引,而不是一個前綴索引。

它會給我所有以'a'開頭的行還是會檢查整列值?

假設你有INDEX(textcol(1))的話,那就必須掃描所有的行與a開始textcol = 'ab'找到行(S)和只提供那些行。請注意,這是一個性能問題,而不是一個正確性問題(正如@Michaelsqlbot雄辯地闡述的那樣)。