mongodb php:统计一组文档中字段的个数

mongodb php: count the number of field in a set of documents

我在 mongodb 库中使用 codeigniter https://github.com/intekhabrizvi/Codeigniter-mongo-library

下面是我的collection"users"。 我想计算来自用户 collection.

的所有具有 badge_slug = 100_club 的徽章

我试过的是

$this->mongo_db->where(array('badges.badge_slug'=>"100_club"))->count('users');

但它只给出了 100_club 的用户数量,无论它是否不止一次。

{
"_id" : ObjectId("57b83ae9faa76bac338b4579"),
"displayname" : "test",
"email" : "test@gmail.com",
"badges" : [
    {
        "awarded_at" : ISODate("2015-04-21T05:52:06Z"),
        "object_id" : "",
        "badge_slug" : "100_club"
    },
    {
        "awarded_at" : ISODate("2015-04-21T06:12:14Z"),
        "object_id" : "",
        "badge_slug" : "100_club"
    },
    {
        "awarded_at" : ISODate("2015-04-21T07:09:55Z"),
        "object_id" : "",
        "badge_slug" : "reader"
    }
]
}
{
    "_id" : ObjectId("57b83ae9faa76bac338b457a"),
    "displayname" : "test2",
    "email" : "test2@gmail.com",
    "badges" : [
        {
            "awarded_at" : ISODate("2015-04-21T06:44:20Z"),
            "object_id" : "",
            "badge_slug" : "100_club"
        }
    ]
}

能否告诉我如何获得用户 collection 中发生的 100_club 的总数。

聚合方法如下,您可以使用 $filter and $size operators to get the count per document and then group all the documents to get the total count. This approach doesn't require using the $unwind 运算符来展平徽章数组,但适用于 MongoDB 3.2 版及更高版本:

mongo shell

var ops = [
    {
        "$project" {
            "count": {
                "$size": {
                    "$filter": {
                        "input": "$badges",
                        "as": "badge",
                        "cond": { "$eq": ["$$badge.badge_slug", "100_club"] }
                    }
                }
            }
        }
    },
    {
        "$group": {
            "_id": null,
            "total": { "$sum": "$count" }
        }
    }
];
db.users.aggregate(ops);

PHP

$ops = array(
    array(
        "$project" => array(
            "count" => array(
                "$size" => array(
                    "$filter" => array(
                        "input" => "$badges",
                        "as" => "badge",
                        "cond" => array("$eq" => => array("$$badge.badge_slug", "100_club") )
                    )
                )
            )
        )
    ),
    array(
        "$group" => array(
            "_id" => null,
            "total" => array( "$sum" => "$count" )
        )
    )
);
$this->mongo_db->aggregate("users", $ops);

对于使用 $unwind 运算符在分组之前先展平徽章数组的方法,请遵循以下示例:

mongo shell

db.users.aggregate([
    { "$match": { "badges.badge_slug": "100_club" }
    { "$unwind": "$badges" },
    { "$match": { "badges.badge_slug": "100_club" },
    {
        "$group": {
            "_id": null,
            "total": { "$sum": 1 }
        }
    }
])