MongoDb选择所有记录并按阵列排序

时间:2016-09-28 09:27:24

标签: mongodb mongodb-query aggregation-framework mongodb-aggregation

在mongoDb中我试图用聚合实现“$ queryResult”中提到的结果,我想从集合中选择所有记录 并在阵列上订购它们,请你帮忙。

以Db记录

$recordsInDb = [
    ["coreId" => 10, "name" => 'a'],
    ["coreId" => 20, "name" =>'a'],
    ["coreId" => 30,"name" => 'a']
];

查询订单

$order = [20,10];

期望的结果

$queryResult = [
    {coreId:20,name:'a'}
    {coreId:10,name:'a'},
    {coreId:30,name:'a'}
]

1 个答案:

答案 0 :(得分:1)

无法想到一个更好的方法,而不是为具有有序列表的集合中的每个文档创建一个额外的数组字段。展开该字段并使用 $unwind 运算符的includeArrayIndex属性生成索引位置。使用该信息然后对文档进行排序,使用额外的tenary运算符 $cond 来计算逻辑表达式array element === coreId,并根据结果返回排序索引,如果为true,否则返回常量n > order.length

以下显示了上述方法,但仍有很大的改进空间,但至少应该给你一些方向。当然,您可以将管道转换为适当的驱动程序语言(我假设是PHP):

var order = [20, 10];
db.records.aggregate([
    { 
        "$project": {
            "coreId" : 1,
            "name" : 1,
            "sortOrder": { "$literal": order } // create an additional field
        }
    },
    { 
        "$unwind": {
            // flatten the above array
            "path": "$sortOrder", 
            // create the index position for each array element
            "includeArrayIndex": "sortIndex", 
        }
    },
    {
        "$project": {
            "coreId": 1,
            "name": 1,
            "sortIndex": {
                 "$cond": [
                    { "$eq": [ "$coreId", "$sortOrder" ] }, 
                    "$sortIndex", 999999 
                 ]
            }
        }
    },
    { "$sort": { "sortIndex": 1 } },
    {
        "$group": {
            "_id": "$coreId",
            "name": { "$first": "$name" },
            "index": { "$first": "$sortIndex" }
        }
    },
    { "$sort": { "index": 1 } },
    { 
        "$project": {
            "_id": 0,
            "coreId" : "$_id",
            "name" : 1
        }
    }
])

示例结果

/* 1 */
{
    "name" : "a",
    "coreId" : 20
}

/* 2 */
{
    "name" : "a",
    "coreId" : 10
}

/* 3 */
{
    "name" : "a",
    "coreId" : 30
}