2017-10-12 93 views
1

內根據具體的情況,從陣列不同的值我有這樣的文檔集合:獲取陣列

{ 
"_id" : ObjectId("59df91dae4b03289d79efb4e"), 
    "name" : "TEST", 
    "payload" : [ 
    { 
     "_id" : "ABC", 
     "status": "FALSE" 
    }, 
    { 
     "_id":"DEF", 
    "status": "TRUE" 
    }, 
    { 
     "_id" : "XYZ", 
    "status": "NULL" 
    } 
    ] 
} 

我試圖找到所有具有的地位TRUE/FALSE的payload._id。 預期的結果是

["ABC","DEF"] 

到目前爲止,我有這樣的事情。

db.collection.distinct('payload._id',{"_id" : "TEST"}) 

不確定如何添加數組中元素的條件。

回答

0

查詢條件與.distinct()適用於「docume NT選擇「而不是包含在文檔」內「的數組條目。如果你需要「過濾」數組內容,那麼你應該使用.aggregate()來代替,以及一個小的後處理來獲得數組響應中的「值」。

db.collection.aggregate([ 
    { "$match": { "_id": "TEST" } }, 
    { "$unwind": "$payload" }, 
    { "$match": { "payload.status": { "$in": ["TRUE","FALSE"] } } }, 
    { "$group": { "_id": "$payload._id" } }, 
]).map(d => d._id); 

存在的主要部分是因爲你想從數組中的值以後使用爲重點,以$group上這樣做主要是$unwind流水線階段。這基本上爲每個數組成員生成一個新文檔,但每個文檔只包含該數組成員。它對包含數組的MongoDB結構是「反常規」。

接下來就是以下$match管道,它與任何查詢一樣工作,只選擇符合條件的文檔。由於所有數組成員現在都是「文檔」,因此將不匹配的條目(作爲文檔)排除在外。你可以交替使用$filter來提取數據,但由於我們需要$unwind進行下一階段,所以我們可能只需要$match

此時,您只剩下符合條件的數組條目。 $group是爲了獲得「不同的」值,所以通常你會通過更廣泛的選擇來做到這一點,而不僅僅是一個單一的文件或任何其中的值不是已經不同。所以這實際上保持了.distinct()的完全相同的行爲。

最後,由於.aggregate()輸出從.distinct()在設計它返回結果的「文件」的區別,我們只需使用.map()方法來處理光標結果和具體的文檔屬性僅返回「值」作爲「陣列」。

+0

這工作。感謝您的解釋。 修改map()方法如下,在RoboMongo上運行 map(function(u){return u。_ID; }) –

+0

@AtulPrasad如果它不理解箭頭'=>'函數的ES6語法,那麼您可能會有舊版本的RoboMongo。我建議你更新一下,因爲還有與現代MongoDB版本兼容性的其他變化。也歡迎Stack Overflow。當您收到適合您問題的答案時[標記爲已接受](https://meta.stackexchange.com/questions/5234/how-does-accepting-an-answer-work)以指示正確的答案。 –

1

我試圖找到所有具有地位TRUE的payload._id/FALSE

要運行的查詢是:

db.collection.distinct('payload._id', { 
    'payload.status': { $in: ["TRUE", "FALSE"] } 
}) 

一個更詳細的方式它會是:

db.collection.distinct('payload._id', { 
    $or: [ 
    {'payload.status': "TRUE" }, 
    {'payload.status': "FALSE" } 
    ] 
}) 
+0

'.distinct()'中的查詢條件不會「過濾」數組內容。 [查看答案](https://stackoverflow.com/a/46718902/2313887)。 –

+0

不起作用。謝謝! –