查询多个日期范围,只返回MongoDB中的特定键
在Mongo中,我有一个如下所示的文档:查询多个日期范围,只返回MongoDB中的特定键,mongodb,Mongodb,在Mongo中,我有一个如下所示的文档: dateRange: [{ "price": "200", "dateStart": "2014-01-01", "dateEnd": "2014-01-30" }, { "price": "220", "dateStart": "2014-02-01", "dateEnd": "2014-02-15" }] 又好又简单,对吧?只是日期和价格。现在,我面临的棘手问题是,如何创建一个查询来查找适合2014
dateRange: [{
"price": "200",
"dateStart": "2014-01-01",
"dateEnd": "2014-01-30"
},
{
"price": "220",
"dateStart": "2014-02-01",
"dateEnd": "2014-02-15"
}]
又好又简单,对吧?只是日期和价格。现在,我面临的棘手问题是,如何创建一个查询来查找适合2014-01-12的日期范围,然后在找到后返回价格,而不是整个日期范围数组
这些日期范围可能会变得相当大,我正在尝试最小化返回的数据量(如果Mongo能够做到这一点的话)。请注意,如果需要,我可以更改日期格式,我只是出于示例目的使用上述格式
感谢您的帮助,谢谢 这个模式的问题在于它使用了大型嵌入式数组——这可能效率很低,因为mongodb查询总是会找到文档,而不是嵌入式对象的子集。即使您使用的是投影,mongodb也必须在内部读取整个对象,因此如果数组变大,比如说100k个条目,这将使事情减速到停止 为什么不简单地将这些数组元素分离到文档中,例如
{
price : 200,
productId : ObjectId("foo"), // or whatever the price refers to
dateStart : "2014-01-01",
dateEnd : "2013-01-30"
}
通过这种方式,mongodb不需要以所有价格拉动整个对象,而只需要与日期范围匹配的价格。这将最大限度地减少传输的数据量。然后,您还可以使用仅返回price
,即db.collection.find({criteria},{price:1,{u id:0})
当然,对象的数量将急剧增加,但有效的索引将解决这个问题。唯一的低效是复制productId
,这比处理大型嵌入式阵列要便宜
注:我建议使用实际日期(ISODate
)而不是字符串,即使它们的格式是可排序的。您希望使用运算符,它仅在2.2版以上版本中有效。您还需要确保使用
编辑:为了清楚起见,您还必须使用注释中指出的
话虽如此,我同意他评论的要点。最好将数组的每个元素表示为单个文档
$elemMatch的快速示例演示投影。只需将$elemMatch添加到查找中即可
> db.test.save ( {
_id: 1,
zipcode: 63109,
students: [
{ name: "john", school: 102, age: 10 },
{ name: "jess", school: 102, age: 11 },
{ name: "jeff", school: 108, age: 15 }
]
} );
> db.test.find( { zipcode: 63109 }, { students: { $elemMatch: { school: 102 } } } ).pretty() );
{
"_id" : 1,
"students" : [
{
"name" : "john",
"school" : 102,
"age" : 10
}
]
}
我同意您必须首先使用
$elemMatch
来查找正确的匹配项(否则,$lt
/$gt
标准将在任何数组索引上匹配),但这并不能避免您返回整个文档,这是OP的问题。$elemMatch进行投影。我明白了,有两种不同的$elemMatch
:查询运算符和投影运算符,后者更新了很多。对于OP的场景,他还必须使用$elemMatch
查询操作符。