使用键名聚合计数数据

时间:2018-06-07 03:51:12

标签: javascript mongodb aggregation-framework

Fisrt,我已将数据汇总到此表格中,如下所示:

查询:

{
 $group:{
     _id:{
     date:"$date"
    ,order_id: "$order_id"
    ,payment_name:"$payment_name" 
         }
        }

}  

汇总结果:

{
    "_id" : {
        "date" : "2018-06-07",
        "order_id" : "180607009399",
        "payment_name" : "creditcard"
    }
}


{
    "_id" : {
        "date" : "2018-06-06",
        "order_id" : "180606009394",
        "payment_name" : "ATM"
    }
}


{
    "_id" : {
        "date" : "2018-06-06",
        "order_id" : "180606009393",
        "payment_name" : "creditcard"
    }
}

{
    "_id" : {
        "date" : "2018-06-07",
        "order_id" : "180606009395",
        "payment_name" : "ATM"
    }
}

然后我想计算每一天的每笔付款。 使用我自己的方法,我可以像这样呈现数据:

查询:

          {
            $group : {
               _id :  { date: "$_id.date",payment_name:"$_id.payment_name" } 
               ,count: { $sum: 1 }
            }
          }
         ,{
            $group : {
               _id :  { date: "$_id.date",payment_name:"$_id.payment_name" }
               ,count:{$sum:"$count"}
            }
          }
         ,{
            $group : {
               _id :  { date: "$_id.date"}
               ,data:{$push:"$$ROOT"}
            }
          }

结果:

 /* 1 */  
     {
        "_id" : {
            "date" : "2018-06-06"
        },
        "data" : [ 
            {
                "_id" : {
                    "date" : "2018-06-06",
                    "payment_name" : "creditcard"
                },
                "count" : 1.0
            }, 
            {
                "_id" : {
                    "date" : "2018-06-06",
                    "payment_name" : "ATM"
                },
                "count" : 1.0
            }
        ]
    }
    /* 2 */  
    {
        "_id" : {
            "date" : "2018-06-07"
        },
        "data" : [ 
            {
                "_id" : {
                    "date" : "2018-06-07",
                    "payment_name" : "creditcard"
                },
                "count_id" : 1.0
            }, 
            {
                "_id" : {
                    "date" : "2018-06-07",
                    "payment_name" : "ATM"
                },
                "count" : 1.0
            }
        ]
    }

但上面的结果看起来有点乱, 我希望表格如下所示。 如何使用付款的价值作为关键,并计算付款价值出现的次数。

 /* 1 */
{
    "_id" : {
        "date" : "2018-06-06"
    },
    "data" :{
            "creditcard" : 1 
            "ATM" : 1
    }

}

/* 2 */
   {
    "_id" : {
        "date" : "2018-06-07"
    },
    "data" :{
            "creditcard" : 1 
            "ATM" : 1
    }

}

1 个答案:

答案 0 :(得分:0)

实际上,您已经完成了"聚合"因此,实际上不需要在数据库端进一步做任何事情。如果你有一个MongoDB 3.4.4或更高版本,那么它实际上有$arrayToObject运算符,可以用你的现有阶段中的一些操作来重塑输出:

db.collection.aggregate([
  { "$group":  {
    "date": "$date",
    "order_id": "$order_id",
    "payment_name": "$payment_name"
  }},
  { "$group": {
    "_id": {
      "date": "$_id.date",
      "payment_type": "$_id.payment_type"
    },
    "count": { "$sum": 1 }
  }},
  { "$group": {
    "_id": { "date": "$_id.date" },
    "data": {
      "$push": {
        "k": "$_id.payment_type",
        "v": "$count"
      }
    }
  }},
  { "$addFields": {
    "data": { "$arrayToObject": "$data" }
  }}
])

"官方"文档说$arrayToObject已添加到MongoDB 3.6中,但实际上它已经进入3.4.4版本并且之后出现在该系列中。

即使您没有超过该版本的版本,您也真的不需要它,并且可以在迭代光标结果时简单地转换文档:

db.collection.aggregate([
  { "$group":  {
    "date": "$date",
    "order_id": "$order_id",
    "payment_name": "$payment_name"
  }},
  { "$group": {
    "_id": {
      "date": "$_id.date",
      "payment_name": "$_id.payment_name"
    },
    "count": { "$sum": 1 }
  }},
  { "$group": {
    "_id": { "date": "$_id.date" },
    "data": {
      "$push": {
        "k": "$_id.payment_name",
        "v": "$count"
      }
    }
  }},
  /*
  { "$addFields": {
    "data": { "$arrayToObject": "$data" }
  }}
  */
]).map(d =>
  Object.assign(
    d,
    {
      data: d.data.reduce((o,e) => Object.assign(o,{ [e.k]: e.v }),{})
    }
  )
)

这是简单的JavaScript转换,并且它在任何语言中都没有太大的不同,因为大多数人都有类似的方法将这些不同的命名键转换为键/值对。

两种形式都产生相同的输出:

[
        {
                "_id" : {
                        "date" : "2018-06-06"
                },
                "data" : {
                        "creditcard" : 1,
                        "ATM" : 1
                }
        },
        {
                "_id" : {
                        "date" : "2018-06-07"
                },
                "data" : {
                        "ATM" : 1,
                        "creditcard" : 1
                }
        }
]