【问题标题】:Get top n values per group in elasticsearch在elasticsearch中获取每组的前n个值
【发布时间】:2016-01-23 04:47:12
【问题描述】:

我需要获得前 n 个用户,因为他们在弹性搜索的不同日期拥有的数字字段的总和。

例如,对于下面的文档获得前 2 个:

doc1 -> user_id: 1, name: hasan, numeric_field: 2, date_calculated: 03-10-2015
doc2 -> user_id: 2, name: veli, numeric_field: 3, date_calculated: 03-10-2015
doc3 -> user_id: 3, name: osman, numeric_field: 1, date_calculated: 03-10-2015
doc4 -> user_id: 1, name: hasan, numeric_field: 3, date_calculated: 04-10-2015
doc5 -> user_id: 2, name: veli, numeric_field: 5, date_calculated: 04-10-2015
doc6 -> user_id: 3, name: osman, numeric_field: 7, date_calculated: 04-10-2015
doc7 -> user_id: 1, name: hasan, numeric_field: 5, date_calculated: 05-10-2015
doc8 -> user_id: 2, name: veli, numeric_field: 8, date_calculated: 05-10-2015
doc9 -> user_id: 3, name: osman, numeric_field: 9, date_calculated: 05-10-2015

按用户分组的 numeric_field 的总和 => hasan : 10, veli : 16, osman : 17

对于这个例子,我需要将结果排在前 2 -> { osman : 17, veli : 16 }

我应该对此有什么类型的查询?

【问题讨论】:

    标签: sorting elasticsearch sum aggregation


    【解决方案1】:

    您需要使用 ElasticSearch 聚合。我正在使用以下查询

    {
      "size": 0,
      "aggs": {
        "user_agg": {
          "terms": {
            "field": "name"
          },
          "aggs": {
            "sum_agg": {
              "sum": {
                "field": "numeric_field"
              }
            }
          }
        }
      }
    }
    

    这是我得到的结果

    "buckets": [
                {
                   "key": "hasan",
                   "doc_count": 3,
                   "sum_agg": {
                      "value": 10
                   }
                },
                {
                   "key": "osman",
                   "doc_count": 3,
                   "sum_agg": {
                      "value": 17
                   }
                },
                {
                   "key": "veli",
                   "doc_count": 3,
                   "sum_agg": {
                      "value": 16
                   }
                }
             ]
    

    我无法获得前 n 个结果。我尝试在 sum 聚合中使用 Top hits 聚合,但事实证明 sum 聚合不支持子聚合。

    您可以尝试对 sum_agg 值进行排序。您可以在此处阅读有关聚合的更多信息。 https://www.elastic.co/guide/en/elasticsearch/reference/master/search-aggregations.html

    我希望这会有所帮助!

    【讨论】:

    • 你不需要在这里使用top_hits,你只是在user_aggterms聚合中缺少"size": 2"order":{"sum_agg": "desc"},它会按预期工作。跨度>
    • @Val 非常感谢!你也解决了我的一个问题
    【解决方案2】:

    @ChintanShah25 的回答和@Val 的评论帮助很大。完整的工作解决方案如下。请注意, shard_size 很重要;如果你不把它设为'0',你可能会看到错误的结果。

    {
      "size": 0,
      "aggs": {
        "user_agg": {
          "terms": {
            "field": "name",
            "shard_size": 0, 
            "size": 2,
            "order": {
                  "sum_agg": "desc"
            }
          },
          "aggs": {
            "sum_agg": {
              "sum": {
                "field": "numeric_field"
              }
            }
          }
        }
      }
    }
    

    【讨论】:

    • 你是对的,没有 shard_size 你经常得到不完整的结果。
    猜你喜欢
    • 2013-07-13
    • 2013-09-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-11-28
    • 1970-01-01
    • 2018-11-15
    相关资源
    最近更新 更多