2011-07-02 32 views
6

我有一組文檔,每個文檔都包含一個子文檔數組。每個子文檔都有一個時間值。我正在嘗試查看是否可以根據子文檔中的時間返回子文檔。MongoDB查詢通過數組中的值檢索一個數組值

我知道我可以使用$ slice檢索子文檔,但$ slice只給我一個特定的索引或範圍和偏移量。

示例時間!

文件是像這樣....

{ 
    id: 1234, 
    type: 'a', 
    subs: [ 
     { time: 123001, val: 'a' }, 
     { time: 123002, val: 'b' }, 
     { time: 123003, val: 'c' } 
    ] 
} 

如果我做查找查詢({},{替補:{$切片:[2,1]}})我回來像:

{ id: 1234, type: 'a', subs: [{ time: 123002, val: 'b' }]} 

我想檢索該記錄,例如基於沒有偏移量,但基於123002時間值。

可能嗎?

去吧!

回答

4

正如你設計的數據這是不可能的。

在MongoDB中,查詢返回整個文檔。您可以過濾特定的字段,但是如果字段的值是一個數組,則它停在那裏。

當您有「對象數組」時,您必須$slice,這不是您想要的,或者您必須以不同方式對數據建模。

在你的情況,下面的結構會讓你的查詢可能:

{ 
    _id: 1234, 
    type: 'a', 
    subs: { 
     '123001': { val: 'a' }, 
     '123002': { val: 'b' }, 
     '123003': { val: 'c' } 
    } 
} 

注意我是如何改變subs成JSON對象而不是數組。現在,你可以做以下查詢,得到的只是你正在尋找的時間:

find({ _id: 1234 }, { 'subs.123002': 1 }) 

這裏最明顯的權衡是,你將不得不改變你使用更改文檔的方式。您不能在subs上使用$push,您無法查詢{'subs.time': 1234},而是必須查詢{'subs.1234': { $exists:true} }

+0

哦,呵呵!是的,這將工作。謝謝。雖然除非我誤解你在說什麼,你可以返回一個文檔的一部分.. http://www.mongodb.org/display/DOCS/Retrieving+a+Subset+of+Fields只是不使用片的數組的一部分。謝謝! – FredArters

+0

如果你使用你的原始結構,你可以做'subs.2'來獲得數組中的第三個元素。但是你通常不知道第三項是什麼。所以對於數組來說,它通常是全或全無。 –

+1

問題是舊的,但也許這對尋找答案的人有用。可以使用$ elemMatch將數組中的一個文檔進行匹配。 http://www.mongodb.org/display/DOCS/Dot+Notation+%28Reaching+into+Objects%29#DotNotation%28ReachingintoObjects%29-Matchingwith%24elemMatch – Esteban