Mongo подсчитывает количество каждого значения для набора документов
У меня есть несколько таких документов:
{
"user": '1'
},
{ "user": '1'
},
{
"user": '2'
},
{
"user": '3'
}
Я хотел бы получить набор всех разных пользователей и их соответствующих счетчиков, отсортированных в порядке убывания. Поэтому мой вывод будет примерно таким:
{
'1': 2,
'2': 1,
'3': 1
}
Я думаю, что это можно сделать с помощью Mongo aggregate(), но у меня много проблем, чтобы понять, как правильно это сделать.
Ответы
Ответ 1
Вы можете получить результат (не в нужном формате) с помощью aggregation
db.collection.aggregate(
{$group : { _id : '$user', count : {$sum : 1}}}
).result
вывод для ваших образцов документов:
"0" : {
"_id" : "2",
"count" : 1
},
"1" : {
"_id" : "3",
"count" : 1
},
"2" : {
"_id" : "1",
"count" : 2
}
Ответ 2
Для тех, кто читает это в январе 2019 года, принятый ответ в настоящее время не работает в Robo3T (возвращает ошибку pipeline.length - 1
).
Вы должны:
а) заключить запрос в набор квадратных скобок []
б) удалить .result
с конца
https://github.com/Studio3T/robomongo/issues/1519#issuecomment-441348191
Вот обновление принятого ответа от @disposer, которое работает для меня в Robo3T.
db.getCollection('collectionName').aggregate(
[ {$group : { _id : '$user', count : {$sum : 1}}} ]
)
Ответ 3
С MongoDb 3.6 и новее вы можете использовать оператор $arrayToObject
и конвейер $replaceRoot
, чтобы получить желаемый результат. Вам необходимо запустить следующий агрегатный конвейер:
db.collection.aggregate([
{ "$group": {
"_id": "$user",
"count": { "$sum": 1 }
} },
{ "$sort": { "_id": 1 } },
{ "$group": {
"_id": null,
"counts": {
"$push": {
"k": "$_id",
"v": "$count"
}
}
} },
{ "$replaceRoot": {
"newRoot": { "$arrayToObject": "$counts" }
} }
])
который дает
{
"1" : 2,
"2" : 1,
"3" : 1
}