Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/mongodb/11.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
通过mongodb聚合中的$max获取完整对象_Mongodb_Aggregation Framework - Fatal编程技术网

通过mongodb聚合中的$max获取完整对象

通过mongodb聚合中的$max获取完整对象,mongodb,aggregation-framework,Mongodb,Aggregation Framework,我有一组需要按masterID或id分组的对象,如果masterID不存在。对于具有相同masterID的一组对象,我需要找到具有最高pos属性的对象($max:“$pos”)。然而,我很难获得最大化pos的完整对象,似乎通过聚合我只能获得pos属性,而不能获得整个对象。下面是我使用的示例聚合,缺少masterID的$ifNull: > db.tst.aggregate([{ "$group": { "_id": "$masterID", "pos": { "$max": "$pos" }

我有一组需要按
masterID
id
分组的对象,如果
masterID
不存在。对于具有相同
masterID
的一组对象,我需要找到具有最高
pos
属性的对象(
$max:“$pos”
)。然而,我很难获得最大化
pos
的完整对象,似乎通过聚合我只能获得
pos
属性,而不能获得整个对象。下面是我使用的示例聚合,缺少
masterID
$ifNull

> db.tst.aggregate([{ "$group": { "_id": "$masterID", "pos": { "$max": "$pos" } } }])
示例对象将是:

> db.tst.find()
{ "_id" : ObjectId("547d6bd28e47d05a9a492e2e"), "masterID" : "master", "pos" : "453", "id" : "hallo" }
{ "_id" : ObjectId("547d6bda8e47d05a9a492e2f"), "masterID" : "master", "pos" : "147", "id" : "welt" }
{ "_id" : ObjectId("547d6be68e47d05a9a492e30"), "masterID" : "master2", "pos" : "1", "id" : "welt" }
所需的聚合结果是:

{ "_id" : ObjectId("547d6bd28e47d05a9a492e2e"), "masterID" : "master", "pos" : "453", "id" : "hallo" }
{ "_id" : ObjectId("547d6be68e47d05a9a492e30"), "masterID" : "master2", "pos" : "1", "id" : "welt" }
是否有办法通过聚合实现此结果,或者我是否需要使用
$push
获取所有分组对象,并在Java代码中围绕聚合实现最大化
pos


此问题表示应在按
pos
排序的对象上使用
$first
$last
,但我看不出如何返回整个对象。

如果我理解正确,您可以尝试以下方法:

db.tst.aggregate([
    { "$sort" : { "pos" : -1 } },
    { 
    "$group": { 
        "_id": { $ifNull: [ "$masterID", "$id" ] },    
           "_Tempid":{$first:"$_id"},
           "masterID":{$first:{ $ifNull: [ "$masterID", "$id" ] }},
           "pos": { "$max": "$pos" },
           "id" : {$first:"$id"}

      }  
  },{
      $project:{
          _id:"$_Tempid",
          "masterID":1,
          "pos":1,
          id:1
      }
  }

])
结果:

{
    "result" : [ 
        {
            "_id" : ObjectId("547d6be68e47d05a9a492e30"),
            "masterID" : "master2",
            "pos" : "1",
            "id" : "welt"
        }, 
        {
            "_id" : ObjectId("547d6bd28e47d05a9a492e2e"),
            "masterID" : "master",
            "pos" : "453",
            "id" : "hallo"
        }
    ],
    "ok" : 1
}

如果我理解正确,您可以尝试以下方法:

db.tst.aggregate([
    { "$sort" : { "pos" : -1 } },
    { 
    "$group": { 
        "_id": { $ifNull: [ "$masterID", "$id" ] },    
           "_Tempid":{$first:"$_id"},
           "masterID":{$first:{ $ifNull: [ "$masterID", "$id" ] }},
           "pos": { "$max": "$pos" },
           "id" : {$first:"$id"}

      }  
  },{
      $project:{
          _id:"$_Tempid",
          "masterID":1,
          "pos":1,
          id:1
      }
  }

])
结果:

{
    "result" : [ 
        {
            "_id" : ObjectId("547d6be68e47d05a9a492e30"),
            "masterID" : "master2",
            "pos" : "1",
            "id" : "welt"
        }, 
        {
            "_id" : ObjectId("547d6bd28e47d05a9a492e2e"),
            "masterID" : "master",
            "pos" : "453",
            "id" : "hallo"
        }
    ],
    "ok" : 1
}

首先按
pos
降序排序。这样,每个
masterID
遇到的第一个文档就是具有最高
pos
的文档。您可以使用
$$ROOT
引用管道中当前正在处理的整个文档

db.tst.aggregate([
    { "$sort" : { "pos" : -1 } },
    { "$group": { 
        "_id": { $ifNull: [ "$masterID", "$_id" ] },
        "max_doc" : { "$first" : "$$ROOT" }
    } }
])

首先按
pos
降序排序。这样,每个
masterID
遇到的第一个文档就是具有最高
pos
的文档。您可以使用
$$ROOT
引用管道中当前正在处理的整个文档

db.tst.aggregate([
    { "$sort" : { "pos" : -1 } },
    { "$group": { 
        "_id": { $ifNull: [ "$masterID", "$_id" ] },
        "max_doc" : { "$first" : "$$ROOT" }
    } }
])

您需要先按
pos
排序,否则
$first
值将来自的文档只是组中按自然顺序排列的第一个文档。您需要先按
pos
排序,或者,
$first
值将来自的文档只是组中按自然顺序排列的第一个文档。我不理解
$$ROOT
。在
$$ROOT
中,在
$sort
之后有一个完整的文档?通过这种方式,您可以执行对象?
$$ROOT
引用当前正在管道中处理的文档。请看,我不理解
$$ROOT
。在
$$ROOT
中,在
$sort
之后有一个完整的文档?通过这种方式,您可以执行对象?
$$ROOT
引用当前正在管道中处理的文档。看见