Mongodb 从数组中获取匹配的嵌入文档

Mongodb 从数组中获取匹配的嵌入文档,mongodb,mongodb-query,aggregation-framework,Mongodb,Mongodb Query,Aggregation Framework,我在MongoDB中有很多文档使用以下结构: { "_id" : ObjectId("..."), "plant" : "XY_4711", "hour" : 1473321600, "units" : [ { "_id" : ObjectId("..."), "unit_id" : 10951, "values" : [ {

我在MongoDB中有很多文档使用以下结构:

{
    "_id" : ObjectId("..."),
    "plant" : "XY_4711",
    "hour" : 1473321600,
    "units" : [
        {
            "_id" : ObjectId("..."),
            "unit_id" : 10951,
            "values" : [
                {
                    "quarter" : 1473321600,
                    "value" : 395,
                },
                {
                    "quarter" : 1473322500,
                    "value" : 402,
                },
                {
                    "quarter" : 1473323400,
                    "value" : 406,
                },
                {
                    "quarter" : 1473324300,
                    "value" : 410,
                }
            ]
        }
    ]
}
现在我需要找到
quarter
位于某些给定时间戳之间的所有嵌入文档值(例如:{$gte:1473324300,$lte:1473328800})

我只从/到获得了用于筛选文档的单位id和季度时间戳。我只需要按单位分组和订购的季度和价值。

我是MongoDB新手,阅读了一些关于
find()
aggregate()
的内容。但我不知道怎么做。服务器上安装了MongoDB 3.0


我终于明白了: 我只需拆开每个阵列,过滤掉我不需要的东西,然后将其重新组合起来:

db.collection.aggregate([ 
    {$match : {$and : [{"units.values.quarter" : {$gte : 1473324300}}, {"units.values.quarter" : {$lte : 1473328800 }}]}}, 
    {$unwind: "$units"}, 
    {$unwind: "$units.values"}, 
    {$match : {$and : [{"units.values.quarter" : {$gte : 1473324300}}, {"units.values.quarter" : {$lte : 1473328800 }}]}}, 
    {$project: {"units": {values: {quarter: 1, "value": 1}, unit_id: 1}}}, 
    {$group: {"_id": "$units.unit_id", "quarter_values": {$push: "$units.values"}}} ,
    {$sort: {"_id": 1}}
])
将提供:

{
    "_id" : 10951,
    "quarter_values" : [
        {
            "quarter" : 1473324300,
            "value" : 410
        },
        {
            "quarter" : 1473325200,
            "value" : 412
        },
        {
            "quarter" : 1473326100,
            "value" : 412
        },
        {
            "quarter" : 1473327000,
            "value" : 411
        },
        {
            "quarter" : 1473327900,
            "value" : 408
        },
        {
            "quarter" : 1473328800,
            "value" : 403
        }
    ]
}
有关详细说明,请参阅


我想我将来必须切换到$map或$filter。感谢ConferenceQuest支持我的问题:)

请参见下面的示例查询。我没有完全理解你的分组要求。但是,通过这个示例查询,您应该能够更改并获得所需的输出

db.collection.aggregate([
    {$unwind : {path : "$units"}},
    {$match : {$and : [{"units.values.quarter" : {$gte : 1473324300}}, {"units.values.quarter" : {$lte : 1473328800 }}]}},
    {$project : {"units" : {values : {quarter : 1, "value" : 1},  unit_id : 1}}},
    {$group : { _id : "$units.unit_id", quarter_values : { $push :{ quarter : "$units.values.quarter", value : "$units.values.value"}}}},
    {$sort : {_id : 1 }}
]);
样本输出:-

{
    "_id" : 10951,
    "quarter_values" : [ 
        {
            "quarter" : [ 
                1473321600, 
                1473322500, 
                1473323400, 
                1473324300
            ],
            "value" : [ 
                395, 
                402, 
                406, 
                410
            ]
        }
    ]
}

要在子文档中进行筛选,您可以简单地用点链接键,如下所示:
db..find({units.values.quarter:{$gte:1473324300,$lte:1473328800})
这样您将获得所有匹配的文档。要仅获取数组值,请查看投影。不过,这不会对嵌入阵列进行排序和分组。谢谢您的提示!我没有考虑过投影是的这正是我想要的!但最后一个问题是:我已经阅读了以下文档。在第一个示例中,光标产生一个格式良好的项数组(示例中名为itemsSold)。我希望有相同的输出(例如
{quarter:1473321600,value:395},{quarter:1473322500,value:402},
。这是由于多个嵌入文档造成的吗?将组更改为{$group:{u id::$units.unit_id],quarter_值:{$push:$units.values},太好了!非常感谢!+1另一个快速问题:为什么我要获取所有嵌入文档(四分之一):1473321600..1473323400在1473324300之前。它们应该被排除在游标中。我只想获取给定时间戳之间的四分之一。我尝试这样做:
“units.values.quarter”:{$gte:1473324300,$lte:1473328800}
。这是因为其他季度符合$lte条件吗?是的,$match选择整个文档。查询需要在$project之后添加其他筛选器以删除其他不必要的值。