ElasticSearch 命令总结

news/2024/5/17 3:01:07/文章来源:https://blog.csdn.net/LUAOHAN/article/details/126695293

目录

      • 0,ES 与关系型数据库类比
      • 1,查看集群信息
      • 2,查看索引信息
      • 3,创建索引
        • 1,创建索引
        • 2,重建索引
      • 4,文档相关操作
        • 1,查看文档
        • 2,写入文档
        • 3,更新文档
        • 4,删除文档
        • 5,并发控制
      • 5,批量操作
        • 1,Bulk 操作
        • 2,Mget 读取
        • 3,Msearch 查询
      • 6,常见错误码
      • 7,数据类型
        • 1,简单类型
        • 2,复杂类型
        • 3,多字段
      • 8,文档的高级查询
        • 1,match_all 查询
        • 2,term 查询
        • 3,terms 查询
        • 4,range 查询
        • 5,exists 查询
        • 6,bool 查询
        • 7,match 查询
        • 8,multi_match 查询
        • 9,match_phrase 查询
        • 10,constant score 查询
        • 11,function score 查询
      • 9,聚合操作
        • 1,统计指标
        • 2,桶聚合
        • 3,先查询再聚合
        • 4,前过滤器
        • 5,聚合排序
      • 10,搜索建议

ElasticSearch 是一款强大的、开源的、分布式的搜索与分析引擎,简称 ES,它提供了实时搜索聚合分析两大功能。

0,ES 与关系型数据库类比

ElasticSearch关系型数据库
索引
文档
字段
Mapping / 映射表定义
DSLSQL

ES 与关系型数据库的区别:

区别ElasticSearch关系型数据库
索引方式倒排索引B-Tree 结构
事务支持不支持支持
扩展方式天生支持分片,易扩展需借助第三方组件进行分库分表,不易使用
查询速度为搜索而生,具有实时性随着数据量的增大,搜索变慢

Mapping 的特点:

  • 用于定义文档中字段的类型
  • 文档中某字段的类型一旦确定就不能更改,因为 ES 会根据相应的类型,去建立索引信息
  • 字段的类型虽然不能更改,但是 Mapping 中可以增加字段

以下是我总结的 ES 的命令。

1,查看集群信息

#  查看 ES 集群信息
> curl http://localhost:9200/ # 查看索引 mappings 
> curl -XGET host:port/$index_name/_mappings?pretty# 查看索引 settings
> curl -XGET host:port/$index_name/_settings?pretty # 查看 ES 中安装的插件
> elasticsearch-plugin list# 安装插件
> elasticsearch-plugin install analysis-icu
  • GET /_cat/plugins?v 查看 ES 中的插件
  • GET /_cluster/health 查看集群的健康状态
  • GET /_cat/nodes?v 查看所有的节点

2,查看索引信息

  • GET /_cat/indices?v 查看所有的索引信息
  • GET /_cat/indices?v&health=green 查看状态为 green 的索引
  • GET /_cat/indices?v&s=docs.count:desc 按照文档个数排序
  • GET /_cat/indices?v&h=i,tm&s=tm:desc 查看索引使用的内存大小
  • GET /_cat/indices/index_prefix*?v&s=index 查看所有的索引名以 index_prefix 为前缀的索引
  • GET /_cat/indices/index_prefix*?pri&v&h=health,index,pri,rep,docs.count,mt 查看指定索引的指定信息

3,创建索引

每个索引都可以定义自己的 Mappings 和 Settings:

  • Mappings:用于设置文档字段的类型。
  • Settings:用于设置不同的数据分布。

1,创建索引

索引操作:

  • PUT $index_name 创建索引
    • 可加入 Mappings 和 Settings 信息(也可不加,采用默认设置)
    • 不可重复创建,否则会报错
    • PUT $index_name/_mapping 创建索引,只有 mapping 信息
    • PUT $index_name/_settings 创建索引,只有 settings 信息
  • HEAD $index_name:查看索引是否存在,通过 http 响应的状态码查看
    • 状态码 200:表示索引存在
    • 状态码 404:表示索引不存在
  • GET $index_name 查看指定索引相关信息(Mappings 和 Settings)
    • GET $index_name/_mapping 只查看 mapping
    • GET $index_name/_settings 只查看 settings
  • DELETE $index_name 删除整个索引,要谨慎使用!
    • 当删除的 index_name 存在时,会删除整个索引内容
    • 当删除的 index_name 不存在时,ES 会返回 404 错误
  • POST $index_name/_close 关闭索引
    • 索引被关闭后,将不再能被使用,直到被打开
  • POST $index_name/_open 打开索引

创建索引:

PUT $index_name
{"mappings":{"properties":{"col_1":{"type":"text"},"col_2":{"type":"keyword"},...}},"settings":{"number_of_shards":5,	# 主分片数,不可更改"number_of_replicas":2	# 副本分片数,默认为 0}
}

虽然 ES 可以自动推断字段的数据类型,但最好还是自定义 mapping,因为,ES 自推断的类型,有可能并不是你想要的。

增加索引字段

虽然索引中的字段的类型是不能改变的,但是可以为索引增加字段。

# 为索引增加字段 col_3,类型为 keyword
POST $index_name/_mapping 
{"properties": {"col_3": {"type":"keyword"}}
}

其实字段类型是否能够修改,分两种情况:

  • 对于新增字段
    • 如果 mappings._doc.dynamicture,当有新字段写入时,Mappings 会自动更新。
    • 如果 mappings._doc.dynamicfalse,当有新字段写入时,Mappings 不会更新;新增字段不会建立倒排索引,但是信息会出现在 _source 中。
    • 如果 mappings._doc.dynamicstrict,当有新字段写入时,写入失败。
  • 对于已有字段
    • 字段的类型不允许再修改。因为如果修改了,会导致已有的信息无法被搜索
    • 如果希望修改字段类型,需要 Reindex 重建索引

dynamic 有 3 种取值,使用下面 API 可以修改 dynamic 的值:

PUT $index_name/_mapping
{"dynamic": false/true/strict
}

2,重建索引

有时候我们需要重建索引,比如以下情况:

  • 索引的 mappings 发生改变:比如字段类型或者分词器等发生更改。
  • 索引的 settings 发生改变:比如索引的主分片数发生更改。
  • 集群内或集群间需要做数据迁移。

ES 中提供两种重建 API:

  • Update by query:在现有索引上重建索引
    • 改变现有 mappings 时,使用该操作
  • Reindex:在其它索引上重建索引
    • 先创建一个新的索引 mappings
    • 再使用 Reindex 迁移数据
# Reindex API
POST _reindex
{"source": { # 指定原有索引"index": "blogs"},"dest": {   # 指定目标索引"index": "blogs_new"}
}

4,文档相关操作

文档的删除与更新:

  • ES 中文档的删除操作不会马上将其删除,而是会将其标记到 del 文件中,在后期合适的时候(比如 Merge 阶段)会真正的删除。
  • ES 中的文档是不可变更的,更新操作会将旧的文档标记为删除,同时增加一个新的字段,并且文档的 version 加 1。

1,查看文档

  • GET $index_name/_count 查看索引中的文档数量
  • POST $index_name/_search 查看指定索引的前10条文档
    • POST Body 是 {}
  • GET $index_name/_doc/$id 获取指定索引中的指定文档

查询性能分析

GET /$index_name/_search
{"profile":"true",	# 开启性能分析"query": {...}
}

评分分析(对某个文档的匹配详情分析):

GET /$index_name/_explain/$doc_id
{"query": {...}
}

2,写入文档

  • POST $index_name/_doc 不指定 ID 写入文档
    • 总是会插入新的文档,文档数加 1
  • PUT $index_name/_doc/$id?op_type=XXX 指定 ID 写入文档
    • op_type=create
      • 相当于 PUT $index_name/_create/$id
      • 当 id 不存在时,会插入新的文档,文档数加 1
      • 当 id 存在时,报错,不会插入新文档
    • op_type=index
      • 相当于 POST/PUT $index_name/_doc/$id
      • 当 id 不存在时,会插入新的文档,文档数加 1
      • 当 id 存在时,会覆盖之前的,并且 version 会加 1,文档数不增加

3,更新文档

  • POST $index_name/_update/$id 更新指定文档的内容。更新的内容要放在 doc 字段中,否则会报错

    • 当 id 不存在时:报错,不更新任何内容
    • 当 id 存在时:
      • 如果更新的字段与原来的相同,则不做任何操作
      • 如果更新的字段与原来的不同,则更新原有内容,并且 version 会加 1
    • 实际上 ES 中的文档是不可变更的,更新操作会将旧的文档标记为删除,同时增加一个新的字段,并且文档的 version 加 1
  • POST $index_name/_update_by_query 根据条件更新文档

条件更新的语法:

POST $index_name/_update_by_query
{"query":{	# 更新条件...},"script":{	# 更新操作...}
}

upsert 操作,表示 update 与 insert

  • 当目标文件存在时,则进行更新操作,否则进行插入操作。

格式如下:

POST /$index_name/_update/$id
{"doc":{			# $id 存在时,进行更新操作"col_1":"xxx","col_2":"yyy"},"upsert" {		# $id 不存在时,进行插入操作"col_1":"mmm","col_2":"nnn"}
}

4,删除文档

  • DELETE $index_name/_doc/$id 删除指定文档
    • 当删除的 id 存在时,会删除该文档
    • 当删除的 id 不存在时,ES 会返回 not_found
  • POST $index_name/_delete_by_query 根据条件删除文档

条件删除格式如下:

POST $index_name/_delete_by_query
{"query":{	# 更新条件...}
}

5,并发控制

同一个资源在多并发处理的时候,会发生冲突的问题。

传统数据库(比如 MySQL)会采用锁的方式,在更新数据的时候对数据进行加锁,来防止冲突。

而 ES 并没有锁,而是将并发问题交给了用户处理。

在 ES 中可以采用两种方式:

  • 内部版本控制(ES 自带的 version):在 URI 中使用 if_seq_noif_primary_term
  • 外部版本控制(由用户指定 version):在 URI 中使用 versionversion_type=external

5,批量操作

  • Bulk 批量操作
  • Mget 批量读取
  • Msearch 批量查询

注意在使用批量操作时,数据量不宜过大,避免出现性能问题,建议在 5~15M

1,Bulk 操作

批量操作指的是,在一次 API 调用中,对不同的索引进行多次操作

  • 每次操作互不影响,即使某个操作出错,也不影响其他操作。

  • 返回的结果中包含了所有操作的执行结果。

Bulk 操作支持 Index,Create,Update,Delete,使用 POST 方法:

POST /_bulk

一般请求体的内容写在文件中,文件名以 .json 结尾。

批量写入的格式

{"index":{"_index":"$index_name", "_id":"1"}}	# 索引名称及 id
{...}											# 索引内容
{"index":{"_index":"$index_name", "_id":"2"}}	# 索引名称及 id
{...}											# 索引内容

如果没有写 _id 字段,则 _id 由 ES 自动生成。

批量更新的格式

{"update":{"_index":"$index_name", "_id":"1"}}	# 索引名称及 id
{"doc":{...}}									# 索引内容
{"update":{"_index":"$index_name", "_id":"2"}}	# 索引名称及 id
{"doc":{...}}									# 索引内容

批量删除的格式

{"delete":{"_index":"$index_name", "_id":"1"}}	# 索引名称及 id
{"delete":{"_index":"$index_name", "_id":"2"}}	# 索引名称及 id

注意,批量 updatedelete 时,必须指定 _id 字段。

一般使用 curl 命令写入:

curl -s -XPOST 'host:port/_bulk?pretty' --data-binary "@xxx.json"

2,Mget 读取

Mget 一次读取多个文档的内容,设计思想类似 Bulk 操作。

语法格式如下:

GET _mget
{"docs" : [{"_index" : "$index_name1", "_id" : "1"},{"_index" : "$index_name2", "_id" : "2"}]
}# 也可以在 URI 中指定索引
GET $index_name/_mget
{"docs" : [{"_id" : "1"},{"_id" : "2"}]
}# 用 _source 字段设置返回内容
GET _mget
{"docs" : [{"_index" : "$index_name1", "_id" : "1"},{"_index" : "$index_name2", "_id" : "2", "_source" : ["f1", "f2"]}]
}

3,Msearch 查询

格式如下:

POST $index_name1/_msearch
{} # 索引名称,不写的话就是 URI 中的索引
{"query" : {"match_all" : {}},"size":1}
{"index" : "index_name2"} # 改变了索引名称
{"query" : {"match_all" : {}},"size":2}# URI 中也可以不写索引名称,此时请求体里必须写索引名称
POST _msearch
{"index" : "index_name1"} # 索引名称
{"query" : {"match_all" : {}},"size":1}
{"index" : "index_name2"} # 索引名称
{"query" : {"match_all" : {}},"size":2}

6,常见错误码

当我们的请求发生错误的时候,ES 会返回相应的错误码,常见的错误码如下:

错误码含义
429集群过于繁忙
4XX请求格式错误
500集群内部错误

7,数据类型

1,简单类型

  • keyword:是不进行切分的字符串类型,主要用于对文档的过滤,排序,聚合
    • 经常用于描述姓名,产品类型,用户 ID,URL,状态码等
    • 查询这种类型,一般使用 term 查询
    • 注意:对 keyword 类型使用 match 查询,是不会命中文档的
  • text:可进行分割的字符串类型
    • 如果希望某字段可以进行模糊查询(match),则可使用该类型
    • 对该类型的查询,一般使用 match 查询(先进行分词,再匹配)
  • 数值类型:一般用于对文档进行过滤,排序,聚合
    • long,interger,short,byte
    • double,float
    • half_float,scaled_float,unsigned_long
    • 对于这类数据类型,一般使用 term,range 查询
  • boolean:有 true 和 false 两种值
    • 该类型一般使用 term 查询
  • date:日期类型
    • ES 中可用如下三种形式表示 date 类型
      • 格式化的日期字符串
      • 秒级别的整型(从 1970.1.1 到现在)
      • 毫秒级的长整型(从 1970.1.1 到现在)
    • ES 中 date 的默认格式是 strict_date_option_time || epoch_millis
      • strict_date_option_time 支持的格式有:
        • yyyy-MM-dd,yyyyMMdd
        • yyyyMMddHHmmss,yyyy-MM-ddTHH:mm:ss
        • yyyy-MM-ddTHH:mm:ss.SSS,yyyy-MM-ddTHH:mm:ss.SSSZ
      • epoch_millis 表示 1970.1.1 到现在的毫秒数
    • 在写入数据时用什么格式,在查询时就用什么格式
    • 一般使用 range 查询对 date 类型进行搜索

注意,date 类型默认不支持我们常用的 yyyy-MM-dd HH:mm:ss 格式,如果需要使用该格式,则需要在 mapping 中定义:

{"mappings": {"properties": {"create_time": {"type":"date",	# 日期类型"format": "yyyy-MM-dd HH:mm:ss"	# 指定格式}}}
}

对 date 类型定义好了格式,就需要使用相应的格式进行写入和查询。

精确值与全文本

ES 中有精确值(Exact Values)与全文本(Full Text)之分,上面说到的数据类型,text 类型属于全文本类型,除了 text 之外,其它都是精确值。

  • 对于精确值,ES 在建立索引和进行搜索时,都不会对文本进行分词分析
    • term,terms,range,exists,bool 查询都属于精确值匹配
  • 对于全文本,ES 在建立索引和进行搜索时,都会对文本进行分词分析
    • 全文本类型适用于 match 查询

2,复杂类型

  • 数组类型:没有特殊的定义方式
    • 在写入时用中括号 [] 括起来就行,它在 mapping 中显示的还是元素的类型,而没有数组类型
    • ES 中的空数组称为 missing field
    • 写入空数组时,将字段值置为 [] 就行,例如 "col_name":[]
    • 对于数组类型的查询规则,遵循其元素的查询规则
  • 对象类型:和数组一样,对象类型也没有特殊的定义方式
    • 在写入文档时,直接写入对象格式就行,ES 会自动将其转化为对象类型
    • 对于对象类型的查询规则,遵循其元素的查询规则
  • geo_point:地理类型

3,多字段

有时,对于同一个字段,需要有不同的索引方式,这时候就需要用到多字段

比如下面的 mapping:

{"mappings": {"properties": {"col_name": {		# 自定义字段名称"type": "text",	# 字段类型"fields": {		# ES 关键字,用于定义多字段"col_name_keyword": {	# 自定义多字段名称"type": "keyword"	# 字段类型}}}}}
}

对于上面的 mapping,ES 在建立索引时,会将 col_name 字段建立两份索引,分别是 text 类型和 keyword 类型。

8,文档的高级查询

指定查询范围

通过 URI 可以指定在哪些索引中进行查询,有下面几种格式:

  • /_search:在所有的索引中进行搜索。
  • /$index_name/_search:在 index_name 索引中进行搜索。
  • /$index1,$index2/_search:在 index1 和 index2 索引中进行搜索。
  • /$index*/_search:在所有的以 index 为前缀的索引中进行搜索。

ES 提供了丰富的查询功能:

  • 进行完全匹配的 term 查询(不进行分词)
  • 按照范围匹配的 range 查询(不进行分词)
  • 进行分词匹配的 match 查询(进行分词)

一个查询模板:

GET /$index_name/_search
{	"query": {		# 查询条件...}"_source": [...],	# 指定返回的字段"sort":[		# 排序方式{"col_name": {"order": "desc"}},...],"from": 0,		# 起始 id"size": 10		# 页大小
}

为了不给 ES 造成较大负担,ES 使用 max_result_window 规定 from + size 的最大值,默认情况下为 10000。

修改该属性的方法(一般无需修改):

PUT /$index_name/_settings
{"index": {"max_result_window": 20000}
}

为了解决深度分页问题,ES 有两种解决方案:Search AfterScroll

不同分页方式的使用场景:

  • 普通查询(不使用分页):需要实时获取顶部的部分文档。
  • From-Size(普通分页):适用于非深度分页。
  • Search After:需要深度分页时使用。
  • Scroll:需要全部文档,比如导出全部数据。

1,match_all 查询

查看索引的所有文档:

# 默认返回前 10 行
GET $index_name/_search
{    "query":{"match_all":{}}
}

match_all 查询不会对文档进行打分,每个文档均为 1.0 分。

2,term 查询

term 查询是结构化精准查询的主要查询方式,用于查询待查字段和查询值是否完全匹配,格式如下:

GET $index_name/_search
{"query": {"term": {				# term 查询"col_name": {		# 字段名称"value": "$xxx"	# 要匹配的值}}}
}

term 查询还有一种简写形式:

GET $index_name/_search
{"query": {"term": {				# term 查询"col_name": "$xxx"	# key:value 形式}}
}

term 查询一般针对的数据类型有:

  • keyword 类型
  • 数值类型
  • 布尔类型
  • 日期类型:要使用 mapping 定义的时间格式
  • 数组类型

3,terms 查询

terms 是 term 的扩展形式,用于查询一个或多个值与待查字段是否完全匹配,格式如下:

GET $index_name/_search
{"query": {"terms": {				# terms 查询"col_name": [		# 字段名称,是一个数组"$xxx",			# 要匹配的值"$yyy","$zzz",...]}}
}

terms 查询一般针对的数据类型有:

  • keyword 类型
  • 数值类型
  • 布尔类型
  • 日期类型:要使用 mapping 定义的时间格式
  • 数组类型

4,range 查询

range 表示范围查询,比较符号有:

  • gt:大于
  • lt:小于
  • gte:大于等于
  • lte:小于等于

格式如下:

GET $index_name/_search
{"query":{"range": {"$col_name": {# 一个或多个比较符号"gte": 300, # 这里 300 加与不加双引号是一样的"lte": 500}}}
}

range 查询一般针对的数据类型有:

  • 数值类型
  • 日期类型:要使用 mapping 定义的时间格式

对于日期类型,ES 内置了几个常用的符号:

符号含义
y
M
w
d
H / h
m
s
now现在

示例:

POST $index_name/_search
{"query" : {"range" : {"$col_name" : {      # 字段名称"gte" : "now-10y"  # 10年之前}}}
}

5,exists 查询

exists 用于查找某个字段不为空的文档,下列情况都表示不为空

  • 值存在,且不是 null
  • 值不是空数组 []
  • 值是数组,但不是 [null]

格式如下:

GET $index_name/_search
{"query":{"exists": {	# 查询 col_name 字段不为空的文档"field": "$col_name"}}
}

搜索不存在某个字段的文档,需要使用布尔查询。

如下:

POST index_name/_search
{"query": {"bool": {       # 布尔查询"must_not": { # 不存在"exists": { # 不存在 $field_name 字段的文档"field": "$field_name"}}}}
}

6,bool 查询

布尔类型支持四种子查询:

  • must:必须匹配,相当于逻辑与(and)
  • should:可以匹配,相当于逻辑或(or)
  • must not:必须不匹配,相当于逻辑非(not)
  • filter:必须匹配过滤条件,不进行打分计算
    • 相当于不打分的 must

这四种子查询都包含一个数组,可以把其他的 term 级别的查询及 bool 查询放入其中。

格式如下:

GET $index_name/_search
{"query": {"bool": {"must/should/must_not/filter": [{"term":{}},{"terms":{}},{"range":{}},{"exists":{}},{"bool":{}},...]}}
}

7,match 查询

match 查询表示全文搜索,主要针对 text 类型,比如一段对话,商品介绍等。

不同于结构化查询,全文搜索会对查询词进行分析(分词),然后再进行查询。

  • 结构化查询关注的是数据是否匹配,一般用于精确匹配
  • 全文搜索关注的是匹配的程度(算分),用于模糊匹配

格式如下:

GET $index_name/_search
{"query": {"match":{		# 先对 $xxx 进行分词,在去字段中匹配"col_name": "$xxx"}}
}

operator 属性

  • 该属性决定文档按照分词后的词集合进行“与”还是“或”匹配
  • 比如分词时分成了 A 和 B
  • operator 用于控制查询时 A 和 B之间的关系
  • 其取值有 and(与关系) 和 or(或关系)
    • A and B 表示包含 A 和 B,它们之间没有先后顺序
    • A or B 表示包含 A 或包含 B,它们之间没有先后顺序
  • 默认为 or

minimum_should_match 属性

  • operator 与关系对于搜索要求过于苛刻,或关系又比较宽松
  • 此时可以使用 minimum_should_match 来控制最小匹配度

语法如下:

POST index_name/_search
{"query": {"match": {"$field_name": {"query": "$xxx","operator": "or","minimum_should_match": 80%}}}
}

8,multi_match 查询

multi_match 表示在多个字段中进行 match。

格式如下:

GET $index_name/_search
{"query": {"multi_match":{"query": "$xxx","fields": [		# 在哪些字段中进行匹配"col_1","col_2",...]}}
}

9,match_phrase 查询

match_phrase 用于搜索确切的短语或邻近的词语。

# 此时表示的含义是
# one 与 love 紧邻,且 one 在 love 前面
# slop 表示 one 与 love 之间可以有几个字符,默认为 1
POST $index_name/_search
{"query": {"match_phrase": {"$field_name":{"query": "one love","slop" : 1}}}
}

10,constant score 查询

默认的查询都会计算算分,constant score 称为不计分查询,所有分数都是 1。boots 属性用于改变分值。

语法如下:

POST $index_name/_search
{"query": {"constant_score": {        # constant_score 查询,固定写法"boost": 2.0,		       # 改变分值,默认为 1"filter": {              # 固定写法"term": {              # constant_score 包装一个 term 查询,就没有了算分"avaliable": true}}}}
}

11,function score 查询

function score 暂略。

9,聚合操作

聚合操作是 ES 提供的第二项重要功能,其使用 aggs 子句。

1,统计指标

常见的统计指标包含以下:

  • avg:平均值
  • max:最大值
  • min:最小值
  • sum:求和
  • stats:同时计算上面 4 种指标
    • 另外还会返回 count,表示参与计算的文档数量
    • 值为空值的字段不会参与计算
  • value_count:专门用于统计字段非空值的数量
    • 注意:如果进行聚合的字段是数组类型,则 value_count 统计的是符合条件的所有文档中该字段数组中非空元素个数的总和,而不是数组的个数总和
  • cardinality:去重统计,类似 MySQL 中的 distinct

格式如下:

GET $index_name/_search 
{"size": 0,	# 聚合操作,size 一般设为 0,表示不需要返回文档信息"aggs": {		# 聚合操作"my_agg": {	# 自定义聚合名称"avg/max/min/sum/stats/value_count": {"field": "$col_name",	# 要进行聚合的字段"missing": 100			# 当字段为空时,用该值替代,不写该属性时,默认为 0}}}
}

对于空值的处理

  • 索引中,会有部分文档,其某些字段可能缺失,或为空值
  • 可以使用 missing 来补充空值

多个统计指标示例:

# 多个 Metric 聚合,找到最低最高和平均工资
POST $index_name/_search
{"size": 0,              # size 为 0"aggs": {"max_salary": {        # 自定义聚合名称"max": {             # 聚合类型"field": "$salary" # 聚合字段}},"min_salary": {        # 自定义聚合名称"min": {             # 聚合类型"field": "$salary" # 聚合字段}},"avg_salary": {        # 自定义聚合名称"avg": {             # 聚合类型"field": "$salary" # 聚合字段}}}
}

2,桶聚合

ES 中的桶聚合相当于 MySQL 中的 Group By 语句,将同一类的数据放入同一个“桶”中。

桶聚合可分为:

  • 单维度桶聚合
  • 多维度桶聚合

单维度桶聚合

单维度桶聚合一般使用以下两种:

  • terms 桶聚合:按照字段的实际完整值进行匹配分组,适用于能够精确匹配的数据类型,比如:
    • keyword 类型
    • bool 类型
    • keyword 数组类型
    • text 类型不适合 terms 桶聚合
  • ranges 桶聚合:针对的是数值类型,表示按照数值范围进行分组,使用到两个关键字:
    • from:起始数值
    • to:终止数值
    • 范围是 [from, to),包含 from,不包含 to

terms 聚合示例:

GET $index_name/_search
{"size": 0,"aggs": {"my_agg": {		# 自定义聚合名称"terms": {"field":"$col_name"	# 按照 $col_name 字段进行聚合# 相当于 MySQL 中的以字段进行 group by 分组}}}
}

默认情况下,进行桶聚合时如果不指定统计指标,则聚合的是文档计数,该值以 doc_count 为 key 存储在每一个 bucket 返回值中。

ranges 聚合示例:

GET $index_name/_search
{"size": 0,"aggs": {"my_agg": {		# 自定义聚合名称"range": {"field":"$col_name",		# 聚合的字段"ranges":[					# 指定多个范围{ "to": 200	},  		# from 默认为 0 { "from": 200, "to": 500 },{ "from": 500, 			# to 默认为该字段最大值"key":"可以使用 key 自定义名称", 	# 如果没有定义 key,ES 会自动生成}			]}}}
}

指定统计指标:在单维度桶聚合的基础上,指定统计指标

# 先以 $col_name1 字段进行桶聚合
# 在其基础上,再对 $col_name2 字段进行聚合
GET $index_name/_search
{"size": 0,"aggs": {"my_agg1": {"terms": {	# 先进行桶聚合"field": "$col_name1"},"aggs": {	# 在桶聚合的基础上,再进行聚合"my_agg2": {"sum" : {	# 求和"field": "$col_name2"}}}}}
}

多维度桶聚合

ES 支持多维度(多层)桶聚合,一层一层的嵌套,如果有统计指标的话,统计指标放在最内层。

例如:

GET $index_name/_search
{"size": 0,"aggs": {"my_level_1": {				# 第一层桶聚合"terms": {"field": "$col_name1"},"aggs": {	"my_level_2": { 	# 第二次桶聚合,在第一层的基础上,再进行桶聚合"terms": {"field":"$col_name2"}"aggs": {		# 最内层,指定统计指标"my_sum" : {"sum" : { 		# 求和"field": "$col_name"}}}}}}}
}

3,先查询再聚合

上面介绍到的都是直接聚合的方式,也就是没有指定 query 子句,是对索引内的所有文档进行聚合。

在加上 query 子句后,参加聚合的文档,必须先匹配 query 查询,才会进行聚合。

GET $index_name/_search
{"size": 0,"query": { 	# query 子句...},"aggs": {	# 聚合子句...}
}

4,前过滤器

只有符合过滤器条件的文档才会进行聚合。

GET $index_name/_search
{"size": 0,"query": { 	# query 子句...},"aggs": {	# 聚合子句"my_agg": {"filter": {  # 前过滤器,与 query 子句语法一样...},"aggs": {	# 真正进行的聚合操作...}}}
}

5,聚合排序

可以使用 order 子句自定义排序方式,可选的排序方式有:

  • 按照文档数排序,使用 _count 关键字
  • 按照聚合指标排序,使用相应聚合名称
  • 按照分组名称排序,使用 _key 关键字

_count 排序:

GET $index_name/_search
{"size": 0,"aggs": {"my_agg1": {"terms": {		# 先进行桶聚合"field": "$col_name1","order": {	# order 子句"_count": "asc"	# 以 my_agg2 的结果进行正序排序}},"aggs": {		# 在桶聚合的基础上,再进行聚合"my_agg2": {"sum" : {	# 求和"field": "$col_name2"}}}}}
}

order 中可以有多个指标:

"order":[{"_count":"asc"}, # 先按照文档数排序{"_key":"desc"}   # 如果文档数相同,再按照 key 排序
]

以聚合名称排序:

"order": {	# order 子句"my_aggs": "asc"	# my_aggs 是自定义聚合名称
}

以分组的组名排序: 也就是引用 buckets 结果中的 key

"order": {	# order 子句"_key": "asc"
}

10,搜索建议

搜索建议就是在用户输入搜索关键词的过程中,系统进行自动补全提示。

在搜索时,用户每输入一个字符,前端就需要向后端发送一次查询请求对匹配项进行查询,因此对后端的响应速度要求很高。

如下是百度的搜索建议:

在这里插入图片描述

ES 中提供的搜索建议功能,使用的索引结构不是倒排索引,而是在内存中构建的 FST,这种数据结构对内存的使用较多,一定要注意。

在 ES 中,要想使用搜索建议,对应的字段类型需要定义为 completion 类型。

PUT $index_name
{"mappings": {"properties": {"$field_name": {		 # 字段名称"type": "completion" # 字段类型}}}
}

使用时,是这样使用的:

GET $index_name/_search
{"suggest": {"my_suggest": {		# 自定义建议名称"prefix": "$用户的输入词","completion": {"field":"$field_name"}}}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.luyixian.cn/news_show_9887.aspx

如若内容造成侵权/违法违规/事实不符,请联系dt猫网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

上海亚商投顾:A股持续调整 券商成做空主力

上海亚商投顾前言:无惧大盘大跌,解密龙虎榜资金,跟踪一线游资和机构资金动向,识别短期热点和强势个股。 市场情绪三大指数今日低开低走,午后均跌超2%,证券、房地产、煤炭等板块跌幅居前。券商股全线下挫&am…

centos8升级宝塔导致的openssl系列问题

故事的发生是这样的,从前有座山 这个问题很古怪,起先是我把宝塔面板从7.9.3升级到7.9.4,结果升级后宝塔弹出 libk5crypto.so.3: undefined symbol: EVP_KDF_ctrl, version OPENSSL_1_1_1b 再后来就是重启的话,连ssh都进不去&…

第137篇 荷兰拍卖

介绍荷兰拍卖,并通过简化版Azuki荷兰拍卖代码,讲解如何通过荷兰拍卖发售 ERC721标准的NFT。 1.荷兰拍卖 荷兰拍卖(Dutch Auction)是一种特殊的拍卖形式。 亦称“减价拍卖”,它是指拍卖标的的竞价由高到低依次递减直到第一个竞买人应价(达到或超过底价)时击槌成交的一种…

05-Java面向对象

文章目录初识面向对象面向过程&面向对象回顾方法及加深对象的创建分析创建与初始化对象构造器详解构造器-无参(默认)构造器-有参创建对象内存分析(简易)面向对象的三大特征封装封装的作用封装演示继承继承示例SuperSuper注意点super VS this方法重写…

Linux 虚拟地址空间

目录 1、一段代码引出一个问题 运行结果: 讨论: 2、Linux下进程虚拟地址空间分布 3、什么是虚拟地址空间? 4、虚拟地址出现之前:进程直接访问物理内存 5、再述虚拟地址空间 虚拟地址空间结构体是如何进行区域划分的呢&…

HTTP1.x协议详解和HTTP2.0笔记

http协议的作用就是指定两个web应用,之间的一种规则,各种特点,管道化,io多路复用,缓存,状态码,都是基于协议之间的字段,和io之间的调度来实现 HTTP的诞生 1989 年 3 月 CERN&#x…

Linux运维笔记[2]-宝塔面板

宝塔面板 宝塔Linux面板是提升运维效率的服务器管理软件,支持一键LAMP/LNMP/集群/监控/网站/FTP/数据库/JAVA等100多项服务器管理功能。 有30个人的专业团队研发及维护,经过200多个版本的迭代,功能全,少出错且足够安全,已获得全球百万用户认可安装。 openEuler安装宝塔面板…

ElasticSearch(九)【SpringBoot整合】

九、SpringBoot整合Elasticsearch 9.1 基本环境配置 创建一个springboot工程springboot-elasticsearch在pom.xml导入依赖 <dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-elasticsearch</artifac…

Kafka3.1简介及Kafka3.1部署、原理和API开发使用介绍

Kafka3.1简介及Kafka3.1部署、原理和API开发使用介绍第1章-kafka简介 1-1.消息队列简介 什么是消息队列 “消息队列”是在消息的传输过程中保存消息的容器。“消息”是在两台计算机间传送的数据单位。 英文名&#xff1a;Message Queue&#xff0c;经常缩写为MQ 可以简单理…

ElasticSearch之Kibana安装及使用

文章目录1. 安装1.11.2 上传安装包并解压1.3 生成证书1.3 修改配置1.4 修改目录拥有者1.5 启动软件1.6 使用Kibana官方介绍&#xff1a;Kibana 是一个免费且开放的用户界面&#xff0c;能够让您对 Elasticsearch 数据进行可视化&#xff0c;并让您在 Elastic Stack 中进行导航。…

[极客大挑战 2020]

[极客大挑战 2020]Roamphp1-Welcome 已进入页面&#xff0c;以为是这道题的环境不对&#xff0c;可是查看f12竟然有东西&#xff0c;然后查一下405 请求方式有误&#xff0c;比如应该用GET请求方式的资源&#xff0c;用了POST 改为post请求方式&#xff0c;出现源码&#xff…

django的settings配置详解

1.介绍 BASE_DIR 默认值&#xff1a;os.path.dirname(os.path.dirname(os.path.abspath(__file__)))。 这个是Django项目文件夹所在目录得绝对路径DEBUG DEBUG 默认值是True。 在本地开发测试环境下设置DEBUGTrue可以显示bug信息&#xff0c;便于开发者找出代码错误所在。 当…

微服务介绍以及远程调用

简介 什么是微服务 微服务是对传统单体服务进行业务拆分&#xff0c;拆分成多个独立的服务。微服务包括服务集群、服务网关、注册中心、配置中心、消息队列、分布式日志服务、系统监控和链路追踪、分布式缓存、分布式搜索、数据库、 Jenkins持续集成服务器以及Docker web自动打…

ECCV2022细粒度图像检索SEMICON代码学习记录

代码链接&#xff1a;GitHub - aassxun/SEMICON 环境配置 # 创建&激活虚拟环境 conda create -n semicon python3.8.5 conda activate semicon# 安装相关依赖包 (该 pytorch 为无 gpu 版本) conda install pytorch1.10.0 torchvision0.11.1 torchaudio0.10.0 cpuonly -c …

你还不会判定表和因果图法的概念及运用?一篇文章教会你

文章末尾给大家准备了大量福利 前言 等价类边界值分析法大家应该都比较熟悉&#xff0c;这两种方法主要针对单个输入类条件的测试&#xff0c;对于输入条件存在关联组合的情况则无法覆盖。如果需要对输入条件进行组合测试&#xff0c;那么就得好好来了解下判定表和因果图法了…

SouthMap平台版省去了安装CAD的诸多麻烦,集成在国产ZWCAD2022平台解决了此瓶颈!!!

SouthMap for ZWCAD2022OEM授权&#xff0c;提取码&#xff1a;6666https://pan.baidu.com/s/1HL-KeGg06Yu7mMFq39QS_A 我们在安装一些行业软件的时候&#xff0c;包括安装和使用过SouthMap时&#xff0c;遇到的第一个拦路虎就是安装AutoCAD&#xff01;虽然AutoCAD功能强大&a…

yolov5 create_dataloader原码及解析

创建数据集的调用关系 create_dataloader&#xff08;…&#xff09;----->LoadImagesAndLabels&#xff08;…&#xff09; create_dataloader part 1 : 参数 def create_dataloader(path,imgsz,batch_size,stride,single_clsFalse,hypNone,augmentFalse,cacheFalse,pad…

编程挑战赛第六期我带我的小侄子来了【赛题解析】

CSDN编程竞赛报名地址&#xff1a;https://edu.csdn.net/contest/detail/16 &#xff08;请不要删掉此地址&#xff09; 努力是为了让自己不平庸&#xff0c; 我被我小侄子拉来参加了CSDN编程竞赛啦&#xff01; 一、前言/背景 前情提要&#xff0c;我家小侄子今年刚上大一&am…

计算机毕业设计之java+SSM酒店客房预定管理系统

计算机毕业设计之javaSSM酒店客房预定管理系统 项目介绍 系统权限按管理员和用户这两类涉及用户划分。 (a) 管理员&#xff1a;管理员使用本系统涉到的功能主要有&#xff1a;个人中心,用户管理,客房类型管理,酒店客房管理,客房预定管理,开房记录管理,退房结账管理,系统管理等功…

6_ROS话题消息(Topic)

这部分教程介绍ROS中Topic的概念以及与Topic相关的rostopic,rqt_plot等工具的使用。至于为什么选择deepin而不是ROS通用的ubuntu,也仅仅是为了支持国产系统。鉴于本人水平有限&#xff0c;如哪位攻城狮网友发现本文存在的问题&#xff0c;烦请留言指正&#xff0c;谢谢! 运行小…