ES聚合查询 基于RestHighLevelClient依赖 Java操作

文章介绍了ES聚合查询的基本流程,包括分组、桶和指标的概念,通过例子展示了如何进行分组统计,如汽车颜色的销量统计。还提到了常用的统计函数,如ValueCount、Cardinality等,并给出了Kibana和Java操作热词检索的示例,强调了桶聚合通常与指标聚合结合使用。

一、介绍 (偏自我理解)

        1.ES聚合查询通用流程

                1.分组 ( 好比Mysql ---> group by )

                2.组内聚合 也叫 组内指标( 好比Mysql ---> SUM()、COUNT()、AVG()、MAX()、MIN() )

        2.桶(我要是es开发者,我起名叫啥都行)

                1.满足特定条件的文档的集合,叫做桶。

                   桶的就是一组数据的集合,对数据分组后,得到一组组的数据,就是一个个的桶

         提示:桶等同于组,分桶和分组是一个意思,ES使用桶代表一组相同特征的数据。

        3.指标

                1.指标指的是对文档进行统计计算方式,又叫指标聚合。

                2.强大之处就是,前面将数据经过一轮桶聚合,把数据分成一个个的桶之后,我们根据上面计算指标对桶内的数据进行统计。

{
  "aggregations" : {
    "<aggregation_name>" : {
        "<aggregation_type>" : {
            <aggregation_body>
        }
        [,"aggregations" : { [<sub_aggregation>]+ } ]? // 嵌套聚合查询,支持多层嵌套
    }
    [,"<aggregation_name_2>" : { ... } ]* // 多个聚合查询,每个聚合查询取不同的名字
  }
}

说明:
1)aggregations - 代表聚合查询语句,可以简写为aggs

2)<aggregation_name> - 代表一个聚合计算的名字,可以随意命名,因为ES支持一次进行多次统计分析查询,后面需要通过这个名字在查询结果中找到我们想要的计算结果。

3)<aggregation_type> - 聚合类型,代表我们想要怎么统计数据,主要有两大类聚合类型,桶聚合和指标聚合,这两类聚合又包括多种聚合类型,例如:指标聚合:sum、avg, 桶聚合:terms、Date histogram等等。

4)<aggregation_body> - 聚合类型的参数,选择不同的聚合类型,有不同的参数。

5)aggregation_name_2 - 代表其他聚合计算的名字,意思就是可以一次进行多种类型的统计。

————————————————
版权声明:本文为CSDN博主「书虫罢了」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/lazyboy2/article/details/125122815

        4.举例说明

下面看个简单的聚合查询的例子:

假设存在一个order索引,存储了每一笔汽车销售订单,里面包含了汽车颜色字段color.

GET /order/_search
{
    "size" : 0, // 设置size=0的意思就是,仅返回聚合查询结果,不返回普通query查询结果。
    "aggs" : { // 聚合查询语句的简写
        "popular_colors" : { // 给聚合查询取个名字,叫popular_colors
            "terms" : { // 聚合类型为,terms,terms是桶聚合的一种,类似SQL的group by的作用,根据字段分组,相同字段值的文档分为一组。
              "field" : "color" // terms聚合类型的参数,这里需要设置分组的字段为color,根据color分组
            }
        }
    }
}

上面使用了terms桶聚合,而且没有明确指定指标聚合函数,默认使用的是Value Count聚合指标统计文档总数, 整个统计的意思是统计每一种汽车颜色的销量。

{
...
   "hits": { // 因为size=0,所以query查询结果为空
      "hits": [] 
   },
   "aggregations": { // 聚合查询结果
      "popular_colors": { // 这个就是popular_colors聚合查询的结果,这就是为什么需要给聚合查询取个名字的原因,如果有多个聚合查询,可以通过名字查找结果
         "buckets": [ // 因为是桶聚合,所以看到返回一个buckets数组,代表分组的统计情况,下面可以看到每一种颜色的销量情况
            {
               "key": "red", 
               "doc_count": 4 // 红色的汽车销量为4
            },
            {
               "key": "blue",
               "doc_count": 2
            },
            {
               "key": "green",
               "doc_count": 2
            }
         ]
      }
   }
}

        5.常用方法

常用的统计函数如下:

  • Value Count - 类似sql的count函数,统计总数
  • Cardinality - 类似SQL的count(DISTINCT 字段), 统计不重复的数据总数
  • Avg - 求平均值
  • Sum - 求和
  • Max - 求最大值
  • Min - 求最小值

        4.上货 (需求:用户搜索热词检索出搜索最多的Top10)

1.首先检索热词,用户在input框输入的时候,每点查询,数据的信息都需要入库,好在咱们es中统计热词

2.插入就不展示了,就说说简单的热词如何分组排序显示。

3.Kibana操作

//先分组看结果 这很关键 是思想的提示
GET XXXXXX/_search
{
  "size": 0,
  "aggs": {
    "order_by_word": { //起的别名
      "terms": {
        "field": "word",
        "size": 10
      }
    }
  }
}

//结果展示
{
  "took" : 3,
  "timed_out" : false,
  "_shards" : {
    "total" : 3,
    "successful" : 3,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 69,
      "relation" : "eq"
    },
    "max_score" : null,
    "hits" : [ ]
  },
  "aggregations" : {
    "order_by_word" : {
      "doc_count_error_upper_bound" : 0,
      "sum_other_doc_count" : 5,
      "buckets" : [ //buckets 桶 下面都是一个桶内不同类型的分桶
        {
          "key" : "宝马",
          "doc_count" : 19 //这就是上面说的默认是Value_count自动聚合分组后的各数量
        },                   我们就是根据这个数量分组后再来排序的不过默认这个关键字为"_count"
        {                
          "key" : "奥迪",
          "doc_count" : 18
        },
        {
          "key" : "奔驰",
          "doc_count" : 16
        },
        {
          "key" : "讴歌",
          "doc_count" : 3
        },
        {
          "key" : "兰博基尼",
          "doc_count" : 2
        },
        {
          "key" : "凯迪拉克",
          "doc_count" : 2
        },
        {
          "key" : "雷克萨斯",
          "doc_count" : 1
        },
        {
          "key" : "雅迪电动车",
          "doc_count" : 1
        },
        {
          "key" : "追风鸟电动车",
          "doc_count" : 1
        },
        {
          "key" : "艾玛电动车",
          "doc_count" : 1
        }
      ]
    }
  }
}
GET lhzz_hot_word/_search
{
  "size": 0,
  "aggs": {
    "order_by_word": {
      "terms": {
        "field": "word",
        "size": 10,
        "order": { //排序 结果和上面一样 默认采用也是倒序 
          "_count": "desc"
        }
      }
    }
  }
}

        我觉得这样再看Java操作就很好理解了 ↓ ↓ ↓ ↓ ↓ ↓

4.Java操作

//搜索索引请求
SearchRequest searchRequest = new SearchRequest("XX_nb_hot_words");
//创建条件数据源
SearchSourceBuilder sourceBuilder = new SearchSourceBuilder();
//聚合查询 top10热词
TermsAggregationBuilder field = AggregationBuilders.terms("order_by_word").field("word")
        //显示满足条件的前10条记录
        .size(10)
        //排序 false是降序 true为升序
        .order(BucketOrder.aggregation("_count", false));
//把聚合条件 添加至 数据源
sourceBuilder.aggregation(field);
//把数据源 添加至 请求中
searchRequest.source(sourceBuilder);
//创建list用于循环接收响应的对象
List<HotWordVO> hotWordList = Lists.newArrayList();
try {
    //返回响应
    SearchResponse response = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT);
    //获取自己起的聚合名称
    Terms terms = response.getAggregations().get("order_by_word");
    for (Terms.Bucket bucket : terms.getBuckets()) {
        HotWordVO hotWordVO = new HotWordVO();
        //咱们指定的 word 字段
        String fieldValue = bucket.getKeyAsString();
        //咱们指定的 word 字段在该索引出现的次数
        long count = bucket.getDocCount();
        hotWordVO.setWord(fieldValue);
        hotWordVO.setCount(count);
        hotWordList.add(hotWordVO);
    }
} catch (IOException e) {
    throw new RuntimeException(e);
}

        将最终结果,包括关键字以及该关键字的出现次数都return给前端,让前端大哥去处理把。

5.福利 (ES聚合用法

本节只使用了最简单的类似SQL的group by的Es Terms()函数 更多细节有很多

ES常用的桶聚合如下:

1)Terms聚合 - 类似SQL的group by,根据字段唯一值分组
2)Histogram聚合 - 根据数值间隔分组,例如: 价格按100间隔分组,0、100、200、300等等
3)Date histogram聚合 - 根据时间间隔分组,例如:按月、按天、按小时分组
4)Range聚合 - 按数值范围分组,例如: 0-150一组,150-200一组,200-500一组。

提示:桶聚合一般不单独使用,都是配合指标聚合一起使用,对数据分组之后肯定要统计桶内数据,在ES中如果没有明确指定指标聚合,默认使用Value Count指标聚合,统计桶内文档总数。

6.ES网上学习资料很多都低于7.0,不适用与现在语法很多都废弃了,所以我也是参照大佬来进行一个自我总结,让我们共同勉励,不断进步把!!!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值