2011-11-30 68 views
2

我有一個蒙戈集合是這樣的:在MongoDB的性能會有所不同


{ 
"A2_AboutMe": "", 
"A2_Attributes": "|av|nv|", 
"A2_Birthday": "", 
"A2_DateCreated": "2010-11-25 22: 59: 00", 
"A2_DateLast": "2011-11-18 12: 09: 36", 
"A2_FK_A1_IDPerson": "0", 
"A2_Firstname": "José Luis", 
"A2_FirstnameC": "Jose Luis", 
"A2_Gender": "m", 
"A2_IDProfile": "1", 
"A2_Keywords": "...|..", 
"A2_Lastname": "test - test", 
"A2_LastnameC": "_test test", 
"A2_Locale": "", 
"A2_Middlename": "", 
"A2_Name": "José Luis test", 
"A2_NameC": "Jose Luis test", 
... 
}

與此集合,8 GB的數據存儲

在 3.000.000文檔上A2_LastnameC和A2_FirstnameC indexies下面的查詢(PHP)在3-4秒內完成

$collection->find(array(«A2_FirstnameC» => new MongoRegex("/jose/i")))->sort(array(«A2_LastnameC» => -1))->limit(10) 

但有時類似的查詢在小於100毫秒內完成。

我能做些什麼來獲得每次這樣的表演嗎?

測試計算機是I7,8GB RAM(7用於通過蒙戈),視窗7

回答

0

首先,索引不會用於不區分大小寫的,不區分大小寫的正則表達式。但在查詢上面的索引可以用於排序A2_LastnameC字段,所以這是很快的。現在有了排序後的數據,MongoDB需要得到A2_FirstnameC的值,並且在10個匹配準備就緒的情況下,它與regexp停止匹配(這也會相對較快,因爲它將使用索引來檢索數據,而不是從磁盤讀取整個文檔)。根據數據順序,它可能會匹配前10個文檔 - 這是最好的情況,它會非常快,最糟糕的情況是在最後10個文檔中發生的匹配必須掃描所有以前的索引條目。

如何加快速度?使用可以使用索引的查詢,如:«A2_FirstnameC» => new MongoRegex("/^jose/")。或者你必須使用某種全文搜索。一個簡單的方法是將字段(您的案例中的A2_Firstname)拆分爲單詞,規範化它們(轉換爲小寫字母,替換重音符號)並將其作爲數組存儲。現在,數組字段的索引將用於快速搜索。

+0

「/^jose /」和「/ jose /」查詢在我的收藏中同時使用。有任何想法嗎? –

+0

@Stefan在某些情況下可以是真實的。你能顯示'explain()'輸出嗎? – pingw33n

+0

明天我會做。現在我重新檢查了我的需求,並希望通過索引數組實現您的方式 –

0

的索引不能被用於不區分大小寫的正則表達式的查詢,也不是爲無根正則表達式(那些不開始與「^」)。由於您已將A2_Firstname字段非規格化爲A2_FirstnameC,因此您還可以將該字段大小寫標準化(即全部小寫或全大寫),並避免使用不區分大小寫的正則表達式;但是即使在這種情況下,如果您沒有使用有根的正則表達式,您仍然可以對集合進行全面掃描。在這種情況下你是否可以使用它取決於你的確切用例。