Как подсчитать логические значения в MongoDB с помощью фреймворка агрегации

Документы хранятся со следующими полями:

_id:
NumberofChildren: Integer
OwnsAHome: Boolean
Income: Integer

Мне нужно использовать структуру агрегации для сортировки по количеству дочерних элементов, чтобы результат был примерно таким:

Number of Children: 3
Number of People: some value, say 17
Number of People who own a home: some value less than 17 which is a sum of the number of true Booleans
Average income: some value

Как мне сделать это в MongoDB с агрегацией, особенно в отношении подсчета количества раз, когда Boolean OwnsAHome равно true?

Спасибо!


person jfeng92    schedule 19.06.2013    source источник


Ответы (2)


Этап $project — ваш друг в конвейере, позволяющий создавать новые поля, которые имеют другие типы и значения, чем исходные поля.

Рассмотрим эту проекцию, которая использует $cond для использования одного значения, когда что-то верно, и другого, когда оно ложно:

{ $project : { numWhoOwnHome : { $cond : [ "$OwnsAHome", 1, 0 ] } } }

Если вы сейчас сделаете $group с {$sum : "$numWhoOwnHome"}, вашим результатом будет количество людей, для которых OwnsAHome установлено в true.

person Asya Kamsky    schedule 19.06.2013
comment
не забудьте добавить в $project для каждого поля, которое вы хотите включить fieldName:1, в противном случае единственным выходом из $project будет поле _id и это новое вычисляемое поле. - person Asya Kamsky; 19.06.2013
comment
{'$group':{.... {count: { $sum: {$cond : [ "$closed", 1, 0 ] }}...} $cond работает в $group с версии 3.2 - person eri; 24.02.2017

Я последовал предложению @eri, используя $cond.

Учитывая данные:

campaign | flags.click | flags.removed
c1       | true        | false
c1       | true        | true
c2       | false       | false

с участием:

Contact.aggregate(
    [
        {
            $group: {
                _id: "$campaign",
                countClick: {
                    $sum: { $cond: ["$flags.click", 1, 0] }
                },
                countRemoved: {
                    $sum: { $cond: ["$flags.removed", 1, 0] }
                },
            }
        }
    ]
).exec();

Я получу вывод:

campaign | countClick | countRemoved
c1       | 2          | 1
c2       | 0          | 0
person Manuel Spigolon    schedule 08.02.2018
comment
Это должно быть помечено как ответ. Нет необходимости в дополнительном этапе проектирования, как это предлагается в ответе от 2013 года. - person slinden; 03.11.2019
comment
@ Мануэль-Спиголон Вы хорошо поработали. - person dipenparmar12; 17.03.2021