MongoDB 如何将集合中的多个对象推入数组

MongoDB how to push multiple objects in a collection into an array

如果我在 mongodb 集合中有多个文档,如下所示:

// document 1
{
    _id: '123',
    date: '5/10/15',

    charges: [{
        amount: 500,
        description: 'foo',
    },{
        amount: 400,
        description: 'bar',
    }],
}


// document 2    
{
    _id: '456',
    date: '5/11/15',

    charges: [{
        amount: 500,
        description: 'foo',
    },{
        amount: 300,
        description: 'foo',
    }],
}

我想创建金额为 500 的所有费用的数组。结果应如下所示:

[{
    amount: 500,
    description: 'foo'
}, {
    amount: 500,
    description: 'foo'
}]

完成此任务最有效的方法是什么?

试试这个:

db.collection.aggregate(
    [
        { 
            $unwind: "$charges"
        },
        {
            $match: {
                amount: 500
            }
        }
    ]
);

在您使用 aggregation framework with $unwind and $group 的文档中:

db.collection.aggregate([
    // Match documents with the required criteria
    { "$match": { "charges.amount": 500 } },

    // Unwind to de-normalize the content
    { "$unwind": "$charges" },

    // Filter the de-normalized documents
    { "$match": { "charges.amount": 500 } },

    // Group back the result
    { "$group": {
        "_id": null,
        "charges": { "$push": "$charges" }
    }}        
])

或者在现代版本中效率更高一点的是先过滤数组:

db.collection.aggregate([
    // Match documents with the required criteria
    { "$match": { "charges.amount": 500 } },

    // Pre filter the array
    { "$redact": {
        "$cond": {
            "if": { "$eq": [{ "$ifNull": [ "$amount", 500 ] }, 500 ]},
            "then": "$$DESCEND",
            "else": "$$PRUNE"
        }
    }},

    // Unwind to de-normalize the content
    { "$unwind": "$charges" },

    // Group back the result
    { "$group": {
        "_id": null,
        "charges": { "$push": "$charges" }
    }}        
])

未来版本(在当前开发版本中工作)将有更有用的$filter方法:

db.collection.aggregate([
    // Match documents with the required criteria
    { "$match": { "charges.amount": 500 } },

    // Filter the array
    { "$project": {
        "charges": {
            "$filter": {
                "input": "$charges",
                "as": "charge",
                "cond": {
                    "$eq": [ "$$charge.amount", 500 ]
                }
            }
        }
    }},

    // Unwind to de-normalize the content
    { "$unwind": "$charges" },

    // Group back the result
    { "$group": {
        "_id": null,
        "charges": { "$push": "$charges" }
    }}        
])

全部结果:

{
    "_id": null,
    "charges": [
        {
            amount: 500,
            description: 'foo'
        }, {
            amount: 500,
            description: 'foo'
        }
    ]
}