Mongodb 查询日期范围
我有以下数据模式:Mongodb 查询日期范围,mongodb,mongodb-query,aggregation-framework,Mongodb,Mongodb Query,Aggregation Framework,我有以下数据模式: { "Address" : "Test1", "City" : "London", "Country" : "UK", "Currency" : "", "Price_History" : { "2014-07-04T02:42:58" : [ { "value1" : 98, "value2" : 98,
{
"Address" : "Test1",
"City" : "London",
"Country" : "UK",
"Currency" : "",
"Price_History" : {
"2014-07-04T02:42:58" : [
{
"value1" : 98,
"value2" : 98,
"value3" : 98
}
],
"2014-07-04T03:50:50" : [
{
"value1" : 91,
"value2" : 92,
"value3" : 93
}
]
},
"Location" : [
9.3435,
52.1014
],
"Postal_code" : "xxx"
}
如何在mongodb中生成查询以搜索介于“2014-07-04T02:42:58”和“2014-07-04T03:50:50”之间的所有结果,或者如何生成查询以仅选择值介于91到93之间的结果,而不知道日期
谢谢,这不是一个很好的建模方法。更好的例子如下:
{
“地址”:“Test1”,
“城市”:“伦敦”,
“国家”:“英国”,
“货币”:“,
“价格历史记录”:[
{“日期”:1,“日期”:ISODate(“2014-07-04T02:42:58Z”),“值”:98},
{“日期输入”:2,“日期”:ISODate(“2014-07-04T02:42:58Z”),“值”:98},
{“日期输入”:3,“日期”:ISODate(“2014-07-04T02:42:58Z”),“值”:98},
{“日期输入”:1,“日期”:ISODate(“2014-07-04T03:50:50Z”),“值”:91},
{“日期输入”:2,“日期”:ISODate(“2014-07-04T03:50:50Z”),“值”:92},
{“dateEntry”:3,“date”:ISODate(“2014-07-04T03:50:50Z”),“value”:93},
],
“地点”:[
9.3435,
52.1014
],
“邮政编码”:“xxx”
}
或者沿着这些路线的一些东西,不使用路径依赖关系。这里的查询相对简单,但也考虑到MongodDB搜索文档而不是数组中类似的内容。但您可以使用聚合框架进行剖析:
db.collection.aggregate([
//仍然首先匹配以减少可能的文档
{“$match”:{
“价格历史记录”:{
“$elemMatch”:{
“日期”:{
“$gte”:ISODate(“2014-07-04T02:42:58Z”),
“$lte”:ISODate(“2014-07-04T03:50:50Z”)
},
“价值”:98
}
}
}},
//放松到“非正常化”
{“$REWIND”:“$Price_History”},
//匹配此时间以“过滤”现在正在生成的数组
{“$match”:{
“价格历史记录日期”:{
“$gte”:ISODate(“2014-07-04T02:42:58Z”),
“$lte”:ISODate(“2014-07-04T03:50:50Z”)
},
“价格与价值”:98
}},
//现在,使用匹配项将每个文档分组
{“$组”:{
“\u id”:“$\u id”,
“地址:{“$first”:“$Address”},
“城市”:{“$first”:“$City”},
“国家”:{“$first”:“$Country”},
“货币”:{“$first”:“$CURRENY”},
“价格历史”:{“$push”:“$Price_History”},
“位置”:{“$first”:“$Location”},
“邮政编码”:{“$first”:“$Postal_Code”}
}}
])
或者最好挂起“规范化”,只处理离散文档,您可以通过标准的.find()
简单地处理这些文档。必须更快更简单
{
“地址”:“Test1”,
“城市”:“伦敦”,
“国家”:“英国”,
“货币”:“,
“日期”:ISODate(“2014-07-04T02:42:58Z”),
“价值”:98
}
等等,那么只需查询:
db.collection.find({
“日期”:{
“$gte”:ISODate(“2014-07-04T02:42:58Z”),
“$lte”:ISODate(“2014-07-04T03:50:50Z”)
},
“价值”:98
})
我真的认为这是一个“非规范化的”“价格历史”集合,因为它效率更高,基本上是聚合语句所模拟的
您请求的查询可以使用诸如MongoDB mapReduce之类的计算JavaScript的工具,但是正如我已经说过的,它需要在没有任何索引帮助的情况下扫描整个集合,这是不好的
现在就把你的情况告诉老板,重新建模并赚取奖金。你的日期不仅是有效的字符串,而且本质上是文档的“关键”。这不是一个好的建模方法,因为“关键路径”是固定的。考虑重新建模或坚持JavaScript评估,这与本地方法相比要慢得多。最好将Pchemice历史更改为一个数组,然后将日期与该天的价格信息进行一个字段,然后使用聚合框架$unwind生成结果,我没有任何选项来更改模式。我这样说。如果不更改模式,则需要扫描集合中的每个记录,以便将“键”的值作为字符串进行比较,并使用JavaScipt求值。每次你想查询的时候。那么,我们是去告诉老板模式需要更改,还是想让老板抱怨为什么你的代码在几个月内表现如此糟糕?Neil首先感谢你的评论,你能发布一个示例(json)吗?如何为这个特定任务设计模式很好,我会提供你的建议,顺便说一句,如果我有一个I.e{“value.com”:98},那么查询看起来如何?因为在这种情况下,您的建议{“Price_Hisotry.value.com”:98}不起作用,或者如果我不知道键“value.com”,查询看起来如何?。再一次thx@ovntatar如果没有一个明确的例子,有点太宽泛了。尝试一下这里的方法,如果你有其他问题,然后张贴一个,我相信有人会回答。