Mongodb将行聚合到列



我有以下数据集。我需要按Account对它们进行分组,然后将Element_Fieldname变成一列。

var collection = [
    {
        Account:12345,
        Element_Fieldname:"cars",
        Element_Value:true
    },
    {
        Account:12345,
        Element_Fieldname:"boats",
        Element_Value:false
    }
]

这是我将行转换为列的尝试,但没有成功。

db.getCollection('my_collection').aggregate([{
            $match : {
                Element_Fieldname : {
                    $in : ["cars", "boats"]
                }
            }
        }, {
            $group : {
                _id : "$Account",
                values : {
                    $addToSet : {
                        field : "$Element_Fieldname",
                        value : "$Element_Value"
                    }
                }
            }
        }, {
            $project : {
                Account : "$_id",
                cars : {
                    "$cond" : [{
                            $eq : ["$Element_Fieldname", "cars"]
                        }, "$Element_Value", null]
                },
                boats : {
                    "$cond" : [{
                            $eq : ["$Element_Fieldname", "day_before_water_bottles"]
                        }, "$Element_Value", null]
                },
            }
        }
    ])

这只是在我的carsboats字段中给了我null。任何帮助都会很棒。

这就是我想要的结果:

var desiredResult = [
    {
        Account:12345,
        cars:true,
        boats:false
    }
]

这是一个很大的技巧,但你会得到你需要的:-)

请在聚合管道的顶部添加$match

db.collection.aggregate([{
            $project : {
                _id : 0,
                "Account" : 1,
                car : {
                    $cond : [{
                            $eq : ["$Element_Fieldname", "cars"]
                        }, "$Element_Value", null]
                },
                boats : {
                    $cond : [{
                            $eq : ["$Element_Fieldname", "boats"]
                        }, "$Element_Value", null]
                },
            }
        },
        {
            $group : {
                _id : "$Account",
                carData : {
                    $addToSet : "$car"
                },
                boatsData : {
                    $addToSet : "$boats"
                }
            }
        }, {
            $unwind : "$carData"
        }, {
            $match : {
                carData : {
                    $ne : null
                }
            }
        }, {
            $unwind : "$boatsData"
        }, {
            $match : {
                boatsData : {
                    $ne : null
                }
            }
        },
    ])

和结果

{
    "_id" : 12345,
    "carData" : true,
    "boatsData" : false
}

不可能使用聚合框架进行所描述的计算类型,但是有一个建议的$arrayToObject表达式,它将为您提供窥探密钥名称和动态创建新密钥/值的功能。

例如,你可以做

db.collection.aggregate([
    {
        "$match": { "Element_Fieldname":{ "$in": ["cars", "boats"] } }
    },    
    {
        "$group": {
            "_id": "$Account",
            "attrs": { 
                "$push": {
                    "key": "$Element_Fieldname",
                    "val": "$Element_Value"
                } 
            }            
        }
    },
    {
        "$project": {
            "Account": "$_id",
            "_id": 0,
            "newAttrs": {
                "$arrayToObject": {
                    "$map": {
                        "input": "$attrs",
                        "as": "el",
                        in: ["$$el.key", "$$el.val"]
                    }
                }
            }
        }
    },
    {
        "$project": {
            "Account": 1,
            "cars": "$newAttrs.cars",
            "boats": "$newAttrs.boats"
        }
    }
])

投票给这张jira票https://jira.mongodb.org/browse/SERVER-23310以获得此功能。


作为一种变通方法,mapreduce似乎是可用的选项。考虑运行以下地图缩减操作:

db.collection.mapReduce(
    function() {
        var obj = {};
        obj[this.Element_Fieldname] = this.Element_Value;        
        emit(this.Account, obj);
    },
    function(key, values) {
        var obj = {};
        values.forEach(function(value) {
            Object.keys(value).forEach(function(key) {                
                obj[key] = value[key];
            });
        });
        return obj;
    },
    { "out": { "inline": 1 } }
)

结果

{
    "_id" : 12345,
    "value" : {
        "cars" : true,
        "boats" : false
    }
}

相关内容

  • 没有找到相关文章

最新更新