【问题标题】:Mongodb Query, search array elements inside document grouping by and counting each elementMongodb查询,搜索文档内的数组元素,按每个元素分组并计数
【发布时间】:2018-08-21 03:37:35
【问题描述】:

假设我有一个包含多个文档的集合,其结构如下:

{
  _id: "id12345",
  objects: ["123","456", "789"]
}

现在我想创建一个查询,在其中传递一个对象数组并获取该数组中每个元素在文档中的出现次数,如下所示:

查询输入:["123","321"] 输出:

{
  "123": 1,
  "321": 0
}

我只想通过一个查询,传递一个数组来做到这一点,我知道我可以很容易地一个一个地做到这一点,而不是一个数组,但这不是目的。

【问题讨论】:

    标签: java mongodb aggregation-framework


    【解决方案1】:

    您可以在 3.6 中使用以下聚合。

    $match 过滤输入数组和对象数组之间至少有一个数组匹配的文档。

    $project$map 迭代输入数组并与对象数组中的每个数组元素进行比较,并根据匹配返回 0 和 1。

    $unwind$group 计算所有文档中数组元素的出现次数。

    db.colname.aggregate([
     {"$match":{"objects":{"$in":["123","321"]}}},
     {"$project":{
       "keyandcount":{
         "$map":{
           "input":["123","321"],
           "in":{
             "k":"$$this",
             "v":{"$cond":[{"$in":["$$this","$objects"]},1,0]}
           }
         }
       }
     }},
     {"$unwind":"$keyandcount"},
     {"$group":{"_id":"$keyandcount.k","count":{"$sum":"$keyandcount.v"}}}
    ])
    

    您可以在末尾添加以下两个阶段来格式化对键值对的响应。

    {"$group":{_id: null,"keycountpair":{"$mergeObjects":{"$arrayToObject":[[["$_id","$count"]]]}}}},
    {"$replaceRoot":{"newRoot":"$keycountpair"}}
    

    【讨论】:

    • 嗨@Veeram,感谢它按预期工作的答案,我需要使用弹簧数据MongoDB来实现这个,我知道“聚合”弹簧操作这是可能的,但我遇到了一些问题$map 操作,使用 spring "mapItemsOf" 函数,你能告诉我这应该是什么样子吗?
    • 不客气。我认为您不能使用mapItemsOf,因为它只需要字段引用或聚合表达式而不是静态数组。您需要准备聚合表达式。类似project().and(new AggregationExpression() { @Override public Document toDocument(AggregationOperationContext aggregationOperationContext) { $map code here } }).as("keyandcount")
    • 您可以使用来自here 的示例并根据您的需要进行调整。
    【解决方案2】:

    一般而言,获取此信息的查询非常简单,因为不建议将值切换到数据层中的键,但更多的是在表示层中。

    所以这个:

    db.collection.aggregate([
      {
        $unwind: "$objects"
      },
      {
        $group: {
          _id: "$objects",
          count: {
            $sum: 1
          }
        }
      }
    ])
    

    会给你_id 的数字和一个带有出现次数的count 字段。然后,您可以在您的应用中对其进行按摩,使其看起来随心所欲。

    Here is a simple example of the result

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-07-17
      • 1970-01-01
      • 1970-01-01
      • 2014-02-25
      • 1970-01-01
      • 2016-06-28
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多