Reputation: 91
I am using MongoDB and the 10Gen node.js driver.
I have a collection in MongoDB that has docs similar to this:
{
_id: ObjectId( "500310affdc47af710000001" ),
name:'something',
tags:['apple','fruit','red'],
created: Date( 1342378221351 )
}
What I would like to get is look at all the documents and get a distinct count of all tags across all documents in the collection. I tried the group function and got this:
> db.photos.group(
... {cond:{}
... ,key:{tags:true}
... ,initial:{count:0}
... ,reduce:function(doc,out){out.count++}
... ,finalize:function(out){}});
[
{
"tags" : null,
"count" : 35
},
{
"tags" : [
"#strawberry",
"#friutpicture"
],
"count" : 1
}
]
Which is not right. I can get the distinct without the counts like this:
> db.photos.distinct('tags')
[
"#friutpicture",
"#strawberry",
"#factory",
"#wallpaper",
"#bummber",
"#test",
"#fire",
"#watermark"
]
but I need the counts.
Upvotes: 2
Views: 2140
Reputation: 42352
You can use the following in the new Aggregation Framework (2.1+):
> db.photos..aggregate([{$unwind:"$tags"},
{$group:{_id:"$tags"}},
{$group:{_id:"DistictCount",count:{$sum:1}}}])
Your result will be:
{
"result" : [
{
"_id" : "DistictCount",
"count" : 8
}
],
"ok" : 1
}
The group function won't do what you need because you need to "unroll" the tag array before you can group on it and that means you need a map function that emits each tag in a document, as well as a reduce. You can use map/reduce if you are stuck on 2.0 or earlier and can't use aggregation framework. Here is an example that may help.
Upvotes: 5