2012-11-02 25 views
7

使用聚合框架,获取每个分组的字段的最大值的最佳方式是什么,以便使用下面的集合我会喜欢具有为具有最新日期的每个group_id返回一个文档的功能。第二个清单显示了所需的结果。通过字段进行汇总并选择另一个字段的最大值作为集合的文档

group_id date 
1  11/1/12 
1  11/2/12 
1  11/3/12 
2  11/1/12 
3  11/2/12 
3  11/3/12 

期望的结果

group_id date 
1  11/3/12 
2  11/1/12 
3  11/3/12 
+3

[?你尝试过什么(http://whathaveyoutried.com) – JohnnyHK

+0

我知道这是不太你要找的,但你可以遍历({group_id:n}).sort({date:-1}).limit(1) - 对于每个group_id = n。通过组ID,执行类似于: db.foo.find 这将按日期对给定组ID的所有文档进行排序,然后仅返回最近的文档。 – Louisa

回答

6

您可以使用在聚合框架的$max分组功能查找每个group_id最新的文档。您需要额外的查询才能根据分组标准检索完整文档。

var results = new Array(); 
db.groups.aggregate(
    // Find documents with latest date for each group_id 
    { $group: { 
     _id: '$group_id', 
     date: { $max: '$date' }, 
    }}, 
    // Rename _id to group_id, so can use as find criteria 
    { $project: { 
     _id: 0, 
     group_id:'$_id', 
     date: '$date' 
    }} 
).result.forEach(function(match) { 
    // Find matching documents per group and push onto results array 
    results.push(db.groups.findOne(match)); 
}); 

示例结果:

{ 
    "_id" : ObjectId("5096cfb8c24a6fd1a8b68551"), 
    "group_id" : 1, 
    "date" : ISODate("2012-11-03T00:00:00Z"), 
    "foo" : "bar" 
} 
{ 
    "_id" : ObjectId("5096cfccc24a6fd1a8b68552"), 
    "group_id" : 2, 
    "date" : ISODate("2012-11-01T00:00:00Z"), 
    "foo" : "baz" 
} 
{ 
    "_id" : ObjectId("5096cfddc24a6fd1a8b68553"), 
    "group_id" : 3, 
    "date" : ISODate("2012-11-03T00:00:00Z"), 
    "foo" : "bat" 
} 
+0

谢谢,那么我怎样才能得到这些作为最大日期的整个文件?我应该在分组后进行投影并明确抓取所有的字段吗? – user1795267

+0

分组将组合文档,这可能不是你想要的。我已经更新了示例以使用聚合框架来查找最新的文档'_id's和'$ in'查询来获取完整的文档。 – Stennie

+2

@Stennie谢谢,这太棒了!但不应该$ max id选择只选择最高_id而不是$ max日期的文档ID?订购在这里重要吗? – Timothy055

相关问题