2008-12-16 70 views
4

我新的數據庫索引,如果我有一個表2列是像例如索引不錯的選擇,分別對2列進行索引和每列的索引有什麼區別?

[Posts]( 
    [PostID] [int] IDENTITY(1,1) NOT NULL, 
    [UserName] [nvarchar](64) NOT NULL, 
    [ApplicationType] [smallint] NOT NULL, 
    ... 
) 

在這種情況下,將帖子ID是主鍵聚集索引,那麼我想要做更多的索引,因爲它是一個大表,我想在UserName和ApplicationType上做,現在我應該單獨索引每一個(UserName上的一個,ApplicationType上的一個)或索引它們作爲一個整體(一個索引在UserName,ApplicationType上)?做壞習慣之前,我可以擁有的索引數量是否有限制?這通常是經驗法則?

謝謝,

雷。

回答

8

請記住複合索引的電話簿規則:電話簿有效地按姓氏,名字進行索引。這是一個複合指數。

如果您搜索名爲「Smith,John」的人,那麼名字是索引的一部分會很有幫助。一旦您找到姓氏爲「Smith」的條目,那麼您可以快速找到「John」。

但是,如果你需要搜索大家都名爲「約翰」,那麼電話簿的索引是沒有用的 - 你必須搜索整本書。

因此,如果您在索引中指定的第一列進行搜索,並且可以選擇第二列等,那麼複合索引非常好。但是,如果搜索跳過索引中最左邊的列,則對於該搜索沒有用處。

2

這個問題的答案真的取決於你如何在桌子上搜索。如果您的搜索幾乎總是包含兩列,那麼在兩列上創建索引都是適當的。如果您將頻繁地在每個字段上自行搜索,則爲每個字段創建單獨的索引是適當的。最後,您可以擁有全部3個索引(一個合成,2個單列) - 具體取決於您如何使用這些列進行搜索。把它看作電話簿 - 如果你總是用姓&的名字搜索,你會發現你要找的。但是如果你想爲Scott的名字搜索電話簿,你需要一個不是(LName,FName)的新索引。如果您想查找給定姓氏的所有人,您仍然可以使用(LName,FName)的多列索引來完成此操作。

每個數據庫對每個表的索引數量,每個索引的列數等都有自己的限制。它們通常足夠高,如果您在這裏查看3個索引,則不必擔心他們。另外,請記住,您擁有的索引越多,維護它們的花費就越多(插入,更新,刪除等)。

1

IIRC,經驗法則是索引只能用於從某個點到左邊使用所有列的查找。例如,如果您在(a),(a,b),(a,b,c)或(a,b,c,d)上查詢,則可以使用列(a,b,c,d)但不在(a,c)上。

這是索引建立方式的結果;索引最左邊的列,然後爲該列的每個值創建下一列的索引等等。


編輯:作爲BQ指出,DBMS可以掃描整個指數的全部「a」部分,做一個查找到「b」部分(我不知道這是實際完成的)。然而,這並不像可以使用上述規則的索引那麼快(OTOH它可能比全表掃描更快)。

就我個人而言,我不認爲這應該是故意槓桿。如果perf對於給定的查詢而言足夠關心,那麼您正在考慮需要哪些索引,那麼您最好給它正確的索引。

+0

對於大多數DBMS的大多數當前版本(和最新版本)而言,這並非如此。通常,如果您在該列'c'中查找某些內容,則更快地掃描索引而不是整個表格。一如既往,分析您的查詢計劃。 – 2008-12-16 22:48:46

+0

很酷。很高興學習新東西。 – BCS 2008-12-16 23:22:35

相關問題