示例数据

# 创建mapping
PUT /hotel
{"mappings": {"properties": {"title": {"type": "text"},"city": {"type": "keyword"},"price": {"type": "double"},"create_time": {"type": "date","format": "yyyy-MM-dd HH:mm:ss"},"amenities": {"type": "text"},"full_room": {"type": "boolean"},"location": {"type": "geo_point"},"praise": {"type": "integer"}}}
}# 导入数据
POST /_bulk
{"index": {"_index": "hotel","_id":"001"}}
{"title": "文雅酒店", "city": "青岛", "price": 556.00, "create_time": "2020-04-18 12:00:00", "amenities": "浴池,普通停车场/充电停车场", "full_room": false, "location": {"lat": 36.083078, "lon": 120.37566},"praise": 10}
{"index": {"_index": "hotel","_id":"002"}}
{"title": "金都嘉怡假日酒店", "city": "北京", "price": 337.00, "create_time": "2021-03-15 20:00:00", "amenities": "wifi,充电停车场/可升降停车场", "full_room": false, "location": {"lat": 39.915153, "lon": 116.4030},"praise": 60}
{"index": {"_index": "hotel","_id":"003"}}
{"title": "金都欣欣酒店", "city": "天津", "price": 200.00, "create_time": "2021-05-09 16:00:00", "amenities": "提供假日part,免费早餐,可充电停车场", "full_room": true, "location": {"lat": 39.186555, "lon": 117.162007},"praise": 30}
{"index": {"_index": "hotel","_id":"004"}}
{"title": "金都酒店", "city": "北京", "price": 500.00, "create_time": "2021-02-18 08:00:00", "amenities": "浴池(假日需预定),室内游泳池,普通停车场", "full_room": true, "location": {"lat": 39.915343, "lon": 116.4239},"praise": 20}
{"index": {"_index": "hotel","_id":"005"}}
{"title": "文雅精选酒店", "city": "北京", "price": 800.00, "create_time": "2021-01-01 08:00:00", "amenities": "浴池(假日需预定),wifi,普通停车场", "full_room": true, "location": {"lat": 39.918229, "lon": 116.422011},"praise": 20}
{"index": {"_index": "hotel","_id":"006"}}
{"title": "完美商务酒店", "city": "东莞", "price": 190.00, "create_time": "2022-04-15 17:24:00", "amenities": "无早餐,wifi,普通停车场", "full_room": false, "location": {"lat": 23.014747, "lon": 113.770511},"praise": 80}

搜索辅助功能

指定返回的字段

_source子句可以设定返回结果的字段。

# 示例
GET /${index_name}/_search
{"_source": ["${field}","${field}"]       # 仅返回指定字段
}

结果计数

_countAPI可以对返回的数据进行数量统计。

# 返回整个索引的文档数
GET /${index_name}/_count# 返回过滤后的文档数
GET /${index_name}/_count
{"query": {"term": {"${field}": {"value": "${value}"}}}
}

结果分页

在默认情况下,ES返回前10个搜索匹配的文档。可以通过设置from和size来定义搜索位置和每页显示的文档数量,from表示查询结果的起始下标,默认值为0,size表示从起始下标开始返回的文档个数,默认值为10。

分页的缺点:当用户查询第n页的时候,实际上es是把前n页的数据全部找出来,再去除前n-1页最后得到需要的数据返回,查最后一页就相当于全扫描。

# 返回20个结果
GET /${index_name}/_search
{"from": 0,"size": 20
}

在默认情况下,用户最多可以取得10000个文档,超过这个值会报错。可以修改max_result_window的值来调整最大限制。

  PUT /${index_name}/_settings{"index": {"max_result_window": 20000         # 设置最大限制为20000}}

滚动查询

scroll适合那种需要一次性或分批拉出大量数据做离线处理、迁移等。

# 语法
GET /${index_name}/_search?scroll=${time}    # time指的是数据保留时间,最大不超过1d,也就是24h
{"size": ${num}
}# 示例
GET /hotel12/_search?scroll=1m    # 查询10条数据,保留1分钟
{"size": 10
}         # 上述命令会返回一个scroll_id,用scroll_id继续查询即可获取后续数据,无需指定索引,因为scroll_id是唯一的
# 重复请求以下api,最后会将全部数据取出
GET /_search/scroll
{"scroll":"1m","scroll_id":"DnF1ZXJ5VGhlbkZldGNoBAAAAAAABPP1FmRFSU9NM1VNU2JxNG9UUlNnSmpXMVEAAAAAAL7OTxYxT0dJOVJVMVFxU2I0N2xCR2IyVzJnAAAAAAC-j70WVVlOZkxQRzJRLXlMRlVMbEQtalBfUQAAAAAAyWm-Fk9HdGx1b3VsUXRLZHV4c1E1OExja0E="
}

性能分析

ES提供了profile功能,该功能详细地列出了搜索时每一个步骤的耗时,可以帮助用户对DSL的性能进行剖析。

# 开启profile功能
GET /${index_name}/_search
{"profile": true,"query": {"match": {"${field}": "${value}"}}
}

评分分析

如果用户不指定按照某个字段进行升序或者降序排列,那么ES会使用打分算法计算的分数对文档进行排序。

ES提供了explain功能来帮助使用者查看搜索时的匹配详情。

# explain使用示例
GET /${index_name}/_explain/${_id}
{"query": {"match": {"${field}": "${value}"}}
}

搜索匹配功能

查询所有文档

使用match_all查询文档时,ES不对文档进行打分计算,默认情况下给每个文档赋予1.0的得分。用户可以通过boost参数设定该分值。

# match_all默认也只会返回10条数据
GET /${index_name}/_search
{"query": {"match_all": {"boost": ${num}   # 设置文档的分值}}
}

关键字别查询

term查询

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

# 语法
GET /${index_name}/_search
{"query": {"term": {"${field}": {"value": "${value}"}}}
}

terms查询

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

GET /${index_name}/_search
{"query": {"terms": {"${field}": [      # 指定查询字段"${value1}",     # 指定查询值,多个值之间用逗号分隔"${value2}","${value3}",...]}}
}

range查询

range查询用于范围查询,一般是对数值型和日期型数据的查询。

范围比较符:

  • gt:大于
  • lt:小于
  • gte:大于或等于
  • lte:小于或等于
# 语法
GET /${index_name}/_search
{"query": {"range": {"${field}": {"${范围比较符}": "${value}"}}}
}# 示例:酒店价格在300-500之间
GET /hotel/_search
{"query": {"range": {"price": {"gte": "300","lte": "500"}}}
}

注意,使用range查询时,查询值必须符合该字段在mappings中设置的规范。意思是不能拿字符串去搜数字类型的范围,会报错。

exists查询

使用exists搜索可以找到某个字段不为空的文档。

字段不为空的条件有:

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

字段为空的条件有:

  • 值是null
  • 值是[](空数组)
  • 值是[null],元素为null的数组
GET /${index_name}/_search
{"query": {"exists": {"field": "${field}"}}
}

布尔查询

must查询

当查询中包含must查询时,表示当前查询为逻辑查询中的“与”查询,被命中的文档必须匹配该查询中的多个子查询结果。

# 语法
GET /${index_name}/_search
{"query": {"bool": {"must": [   # 可以包含多个[关键字级别查询](https://www.wolai.com/oY96bxtB5oQV9ZvaZfb9Eg#9v5dJHAJNQhHjef65M5wWa)和[布尔查询](https://www.wolai.com/oY96bxtB5oQV9ZvaZfb9Eg#pM18FZBFcZkW4wrb7ZVJJH){# term查询},{# range查询或exists查询}]}}
}# 示例:查询北京价格在350-500之间的酒店
GET /hotel/_search
{"query": {"bool": {"must": [{"term": {"city": {"value": "北京"}}},{"range": {"price": {"gte": 350,"lte": 500}}}]}}
}

should查询

当查询中包含should查询时,表示当前查询为逻辑查询中的“或”查询。被命中的文档可以匹配该查询中的一个或多个子查询结果。

# 语法
GET /${index_name}/_search
{"query": {"bool": {"should": [   # 可以包含多个[term级别查询](https://www.wolai.com/oY96bxtB5oQV9ZvaZfb9Eg#9v5dJHAJNQhHjef65M5wWa)和布尔查询{# term查询},{# range查询或exists查询}]}}
}# 示例:查询北京或者天津的酒店
GET /hotel/_search
{"query": {"bool": {"should": [{"term": {"city": {"value": "北京"}}},{"term": {"city": {"value": "天津"}}}]}}
}

must_not查询

当查询中包含must_not查询时,表示当前查询为逻辑查询中的“非”查询,被命中的文档必须不匹配该查询中的多个子查询结果。

# 语法
GET /${index_name}/_search
{"query": {"bool": {"must_not": [   # 可以包含多个term级别查询和布尔查询{# term查询},{# range查询或exists查询}]}}
}# 示例:查询不是北京或者天津的酒店
GET /hotel/_search
{"query": {"bool": {"must_not": [{"term": {"city": {"value": "北京"}}},{"term": {"city": {"value": "天津"}}}]}}
}

filter查询

filter查询即过滤查询,排除不匹配的文档。

区别:

  • 其他布尔查询关注的是查询条件和文档的匹配程度,并按照匹配程度进行打分
  • 而filter查询关注的是查询条件和文档是否匹配,不打分,但是会对部分匹配结果进行缓存。
# 语法
GET /${index_name}/_search
{"query": {"bool": {"filter": [   # 可以包含多个term级别查询和布尔查询{# term查询},{# range查询或exists查询}]}}
}# 示例:查询北京不满房的酒店
GET /hotel/_search
{"query": {"bool": {"filter": [{"term": {"city": {"value": "北京"}}},{"term": {"full_room": false}}]}}
}

Constant Score查询

Constant Score查询可以过滤出某个文本字段是否包含某个词,但是会忽略TF(Term Frequency,检索词频率),也就是会忽略搜索关键字在文档中的次数。

# 语法
GET /${index_name}/_search
{"query": {"constant_score": {"filter": {# 可以加各种搜索方式,如term、match、bool等}}}
}# 示例:查询amenities字段包含关键词“停车场”的酒店
GET /hotel/_search
{"_source": ["amenities"],"query": {"constant_score": {"filter": {"match": {"amenities": "停车场"}}}}
}     # 输出结果中,无论“停车场”出现几次,分数都是1,boost可以修改分数

Function Score查询

Function Score查询通过函数来控制文档的相关度,从而影响排序结果。

# 语法
GET /${index_name}/_search
{"query": {"function_score": {"query": {},"functions": [{}]}}
}# 示例
GET /hotel/_search
{"_source": ["title","city"], "query": {"function_score": {"query": {                  # 查询语句为term查询"term": {"city": {"value": "北京"}}},"functions": [              # 使用随机分数函数{"random_score": {}     }],"score_mode": "sum"         # 最终分数设置为各个函数结果的总和}}
}

全文搜索

全文搜索首先对查询词进行分析,然后根据查询词的分词结果构建查询。

match查询

match查询只要分词中的一个或者多个在文档中存在即可。

# 语法
GET /${index_name}/_search
{"query": {"match": {"${field}": "${value}"}}
}# 示例:默认分词器会拆分成“金”“都”“酒”“店”,因此,只要文档中包含这4个字中的任何一个字,都会被搜索到
GET /hotel/_search
{"_source": ["title"],"query": {"match": {"title": "金都酒店"}}
}

multi_match查询

multi_match查询可以在多个字段中查询关键词。

# 语法
GET /${index_name}/_search
{"query": {"multi_match": {"query": "${value}","fields": ["${field}",...]}}
}# 示例
GET /hotel/_search
{"_source": ["title","amenities"], "query": {"multi_match": {"query": "假日","fields": ["title","amenities"]}}
}

match_phrase查询

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

# 语法
GET /${index_name}/_search
{"query": {"match_phrase": {"${field}": "${value}"}}
}# 示例
GET /hotel/_search
{"query": {"match_phrase": {"title": "文雅酒店"}}
}      # 只会在示例数据中匹配”文雅酒店“,不会匹配”文雅精选酒店“

基于地理位置查询

对于geo_point字段类型的查询方式有3种,分别为geo_distance查询、geo_bounding_box查询和geo_polygon

geo_distance查询

geo_distance查询方式需要用户指定一个坐标点,在指定距离该点的范围后,ES即可查询到相应的文档。

GET /hotel/_search
{"_source": ["title","city","location"], "query": {"geo_distance": {"distance": "5km",            # 指定范围为5km"location": {                 # 设置指定坐标点的纬度、精度"lat": "39.915143","lon": "116.4039"}}}
}

搜索建议

搜索建议:即在用户输入搜索关键词的过程中系统进行自动补全。

当字段的类型定义为completion时,才可以使用Completion Suggester提供的搜索建议功能。

GET /hotel_sug/_search
{"suggest": {"hotel_zh_sug": {             # 定义搜索建议的名称"prefix": "如家",           # 设置搜索建议的前缀"completion": {            # 设置搜索建议对应的字段"field": "query_word"}}}
}

排序功能

在默认情况下,ES对搜索结果是按照相关性降序排序的。

ES提供了sort子句可以对数据进行排序。使用sort子句一般是按照字段信息进行排序,不受相关性影响,而且打分步骤需要耗费一定的硬件资源和时间,因此默认情况下,不对文档进行打分。

按普通字段值排序

sort默认是升序,即asc,可通过order字段设置为降序,即desc。

# 语法
GET /${index_name}/_search
{"sort": [{"${field}": {"order": "desc"        # 设置为降序排列}}]
}# 示例
GET /hotel/_search
{"_source": ["title","price"],"query": {"match": {"title": "金都"}},"sort": [                    # sort是个数组,可以按照多个字段进行排序{"price": {"order": "desc"}}]
}

按地理距离排序

GET /hotel/_search
{"_source": ["title","city","location"],"query": {"geo_distance": {"distance": "5km",             # 查询的地理范围"location": {                  # 设置的中心点坐标"lat": "39.915143","lon": "116.4039"}}},"sort": [{"_geo_distance": {"location": {                # 设置排序的中心点坐标"lat": "39.915143","lon": "116.4039"},"order": "asc",              # 距离由近到远"unit": "km",                # 排序所使用的距离单位"distance_type": "plane"     # 排序所使用的距离算法,默认算法是arc(精准但是耗时长),plane则相反}}]
}

Elasticsearch搜索操作相关推荐

  1. elasticsearch实战三部曲之三:搜索操作

    elasticsearch实战三部曲之三:搜索操作 2019年01月13日 21:35:18 博陵精骑 阅读数:1367 标签: elasticsearch 更多 个人分类: elasticsearc ...

  2. ElasticSearch搜索详细讲解与操作

    全文检索基础 全文检索流程 流程: #mermaid-svg-7Eg2qFEl06PIEAxZ {font-family:"trebuchet ms",verdana,arial, ...

  3. kotlin + springboot启用elasticsearch搜索

    参考自: http://how2j.cn/k/search-engine/search-engine-springboot/1791.html?p=78908 工具版本: elasticsearch ...

  4. ElasticSearch搜索底层基础原理总结

    目录: 1._search结果分析 2.multi-index和multi-type 3.分页查询与deep paging 4.query DSL和query string 5.mapping 6.倒 ...

  5. 分布式搜索elasticsearch搜索功能【深入】

    elasticsearch搜索功能[深入] 分布式搜索elasticsearch搜索功能[深入] 1.数据聚合 1.1 聚合的种类 1.2 DSL实现聚合 1.2.1 Bucket聚合 1.2.2 M ...

  6. ElasticSearch(搜索服务器)-第一天

    1为什么使用es ElasticSearch 搜索服务器.简称es. 初识es 搜索时数据库的问题 2.1是什么 搜索服务器 软件 2.1.1互联网搜索 https://www.baidu.com/ ...

  7. Elasticsearch 搜索测试与集成Springboot3

    Elasticsearch是专门做搜索的,它非常擅长以下方面的问题 Elasticsearch对模糊搜索非常擅长(搜索速度很快) 从Elasticsearch搜索到的数据可以根据评分过滤掉大部分的,只 ...

  8. 详细描述一下Elasticsearch搜索的过程

    详细描述一下Elasticsearch搜索的过程 我们都知道es是一个分布式的存储和检索系统,在存储的时候默认是根据每条记录的_id字段做路由分发的,这意味着es服务端是准确知道每个document分 ...

  9. 基于octree的空间划分及搜索操作

    (1)  octree是一种用于管理稀疏3D数据的树形数据结构,每个内部节点都正好有八个子节点,介绍如何用octree在点云数据中进行空间划分及近邻搜索,实现"体素内近邻搜索(Neighbo ...

最新文章

  1. Skin设计小组新作品发布—CornflowerBlue
  2. 页面左边导航固定,右边自适应宽度
  3. PHP学习记录(字符串函数)
  4. python udp数据报
  5. QML从右到左的用户界面
  6. 在我看来,代码审查就是在排大便...
  7. 四川大学计算机专业调剂,2019四川大学计算机学院考研调剂信息(第二批)
  8. Android音视频开发之ExoPlayer(二):播放列表常用的功能
  9. 状态码406解决方式
  10. 单词前缀dia/dis/duo/en/epi/eu等衍生单词(辅助记忆)
  11. kafka auto.offset.reset / latest / earliest 详解
  12. FTP显示文件的修改时间与实际时间不一致
  13. Redis 在windows中启动
  14. 用Google搜索本地硬盘
  15. 彻底清除已删除的文件
  16. 【Android开发】 获取手机上的各种apk的包名和类名,实现跳转到其他应用
  17. 【文献笔记】【部分精读】【CIR】Angle of Arrival Estimation based on Channel Impulse Response Measurements
  18. 中国广电网络股份有限公司46位股东出资情况大揭秘!
  19. iOS 利用宏判断系统版本
  20. 系统架构设计笔记(59)—— 嵌入式系统的组成

热门文章

  1. javaweb项目图书借阅管理系统设计与实现(有文档+调试视频教程+项目源码).rar
  2. 云计算机能不能玩游戏,云电脑有哪些?可不可以拿来玩steam游戏?
  3. 知乎问 想找一个linux培训机构,目前看千峰、黑马、达内 北大青鸟等机构,请问哪个好一点?
  4. 使用Navicat 连接oracle “ORA-03135: Connection Lost Contact”
  5. python计算学生平均年龄_不能理解平均年龄的计算
  6. Android 适配暗黑模式
  7. 智美2.0 文字格式化
  8. html中如何实现a标签的点击事件
  9. Java+OpenCV实现图片中的人脸识别
  10. 【python】秀人集-写真集-爬虫-2.0