查询MongoDB中的数组

时间:2017-05-13 10:23:11

标签: mongodb mongodb-query

假设在集合中我有以下文件:

[
  {"title": "t1", "fingerprint":[1, 2, 3]},
  {"title": "t2", "fingerprint":[4, 5, 6]}
]

我想查询文档,其中指定位置的指纹中至少有一个元素等于我的查询数组。 例如: 查询([1,7,9])应该返回[{"title": "t1", "fingerprint":[1, 2, 3]}]

查询([1,5,9])应该返回[{"title": "t1", "fingerprint":[1, 2, 3]}, {"title": "t2", "fingerprint":[4, 5, 6]}]

但是查询([5,1,9])应该不返回任何记录,因为两个记录在指纹数组中的任何位置都没有相同的值。 如何编写给定的查询?

3 个答案:

答案 0 :(得分:2)

当您尝试仅匹配序列[1 2,3]出现在values字段中且仅按照确切顺序排列的数组时,您可以这样做:

db.testcol.find()
{ "_id" : "first", "value" : [ 1, 2, 3 ] }
{ "_id" : "second", "value" : [ 4, 5, 6 ] }
{ "_id" : "third", "value" : [ 1, 12, 13 ] }
{ "_id" : "fourth", "value" : [ 3, 2, 1 ] }
{ "_id" : "fifth", "value" : [ 1, 12, 13, 2, 3 ] }
{ "_id" : "sixth", "value" : [ 3, 2, 1, 2, 3 ] }
> db.testcol.aggregate([{$addFields:{ 
   cmp: {$in:[ 
      {$literal:[1,2,3]}, 
      {$map: {
         input:{$range:[0, {$subtract:[{$size:"$value"},2]}]}, 
         as:"l", 
         in: {$slice: [ "$value", "$$l", 3] } 
      }}
   ]}
}}])
{ "_id" : "first", "value" : [ 1, 2, 3 ], "cmp" : true }
{ "_id" : "second", "value" : [ 4, 5, 6 ], "cmp" : false }
{ "_id" : "third", "value" : [ 1, 12, 13 ], "cmp" : false }
{ "_id" : "fourth", "value" : [ 3, 2, 1 ], "cmp" : false }
{ "_id" : "fifth", "value" : [ 1, 12, 13, 2, 3 ], "cmp" : false }
{ "_id" : "sixth", "value" : [ 3, 2, 1, 2, 3 ], "cmp" : true }

$addFields阶段的作用是检查[1,2,3]是否出现在从value数组的位置0开始的三个元素数组的列表中,并向前移动到结束前的两个位置。< / p>

正如您所看到的,添加$match阶段来过滤掉cmp不正确的文档现在变得微不足道了。

答案 1 :(得分:1)

您可以使用.$index表示法执行此类搜索。

query([1, 7, 9])

的示例
db.coll.find({$or: [{"fingerprint.0": 1}, {"fingerprint.1": 7 }, {"fingerprint.2": 9}]})
{ "_id" : ObjectId("59170da907e34e73c0c93a9b"), "title" : "t1", "fingerprint" : [ 1, 2, 3 ] }

query([1, 5, 9])

db.coll.find({$or: [{"fingerprint.0": 1}, {"fingerprint.1": 5 }, {"fingerprint.2": 9}]})
{ "_id" : ObjectId("59170da907e34e73c0c93a9b"), "title" : "t1", "fingerprint" : [ 1, 2, 3 ] }
{ "_id" : ObjectId("59170da907e34e73c0c93a9c"), "title" : "t2", "fingerprint" : [ 4, 5, 6 ] }

答案 2 :(得分:0)

$ in运算符用于将值与值列表进行匹配。

根据上述说明,请尝试在MongoDB shell中执行以下查询

db.collection.find({fingerprint:{$in:[1,7,9]}})