【问题标题】:MongoDB aggregation - group by multiple keys with count for every level of groupingMongoDB 聚合 - 按多个键分组,每个级别的分组都有计数
【发布时间】:2020-08-30 04:14:42
【问题描述】:

我有一个平面文档结构,我试图根据多个键组合在一起。 文档的结构是这样的

[{
  "_id": ObjectId("5f47eee763f55a095048f542"),
  "channel": "Z_C",
  "city": "A",
  "status": 0
},
.
.

city、channel 可以有不同的值,status 只能是 0 或 1。 我正在尝试获得这样的分组结果

[{
  "city": "A",
  "channels": [
  {

    "name": "Z_C",
    "counts":[
        {"status": 0,"count": 7},
        {"status": 1,"count": 2},
    ],
    "count": 9
  },
  {
    "name": "S_C",
    "counts":[
        {"status": 0, "count": 2},
        {"status": 1,"count": 9},
    ],
    "count": 11
  }
],
"count": 20
},
.
.

从上面的结果我们可以得出结论

  1. A市有两个通道Z_C和S_C
  2. Z_C 有 7 个状态为 0 的值和 2 个状态为 1 的值,总 Z_C 为 9
  3. S_C 有 2 个状态为 0 的值和 9 个状态为 1 的值,总 S_C 为 11
  4. A 市的值总数为 20。

我不需要完全像上面提到的结果结构,只要我能从结果中得出 4 个点。

我已经做到了,这是我迄今为止所做的code on mongo playground

{
  "_id": {
    "city": "A"
  },
  "channels": [
    {
    "count": 7,
    "name": "Z_C",
    "status": 0
  },
  {
    "count": 2,
    "name": "S_C",
    "status": 0
  },
  {
    "count": 9,
    "name": "S_C",
    "status": 1
  },
  {
    "count": 2,
    "name": "Z_C",
    "status": 1
  }
],
"count": 20
}

如何根据通道对内部通道数组进行分组以获得预期结果?

谢谢。

【问题讨论】:

    标签: mongodb aggregation-framework


    【解决方案1】:

    您可以使用三个组,

    • 你在第一组几乎是对的
    db.collection.aggregate([
      {
        $group: {
          _id: {
            city: "$city",
            name: "$channel",
            status: "$status"
          },
          count: { $sum: 1 }
        }
      },
    
    • 只需要使用城市和频道名称进行分组,因为我们需要为状态准备(构造)计数数组
      {
        $group: {
          _id: {
            city: "$_id.city",
            name: "$_id.name"
          },
          counts: {
            $push: {
              count: "$count",
              status: "$_id.status"
            }
          },
          count: { $sum: "$count" }
        }
      },
    
    • 按城市排序
      { $sort: { "_id.city": 1 } },
    
    • 最终构造通道数组
      {
        $group: {
          _id: "$_id.city",
          channels: {
            $push: {
              name: "$_id.name",
              counts: "$counts",
              count: "$count"
            }
          },
          count: { $sum: "$count" }
        }
      }
    ])
    

    Playground

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-07-03
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-03-28
      相关资源
      最近更新 更多