详解SpringCloud微服务技术栈:DSL查询ES文档高级语法、相关性算分数学原理总结

👨‍🎓作者简介:一位大四、研0学生,正在努力准备大四暑假的实习
🌌上期文章:详解SpringCloud微服务技术栈:ElasticSearch实践1——RestClient操作索引库与文档
📚订阅专栏:微服务技术全家桶
希望文章对你们有所帮助

之前已经使用了DSL实现了索引的增删改查以及文档的增删改,并且通过RestClient进行实现。
但是文档的查询操作很复杂,并且分类比较多,所以先用DSL语句进行各种查询操作的实现,再用RestClient实现各类查询。

DSL查询ElasticSearch文档

  • DSL查询分类和基本语法
  • 全文检索查询
  • 精确查询
  • 地理查询
  • 复合查询
    • 相关性算分
    • Function Score Query
    • Boolean Query

DSL查询分类和基本语法

ElasticSearch提供了基于JSON的DSL来定义查询,常见查询的分类:

1、查询所有:查询出所有数据,一般测试的时候用,例如match_all
2、全文检索(full text)查询:利用分词器对用户输入内容分词,然后去倒排索引库中匹配,例如:
(1)match_query
(2)multi_match_query
3、精确查询:根据精确词条值查找数据,一般是查找keyword、数值、日期、boolean等类型字段,例如:
(1)ids
(2)range
(3)term
4、地理(geo)查询:根据经纬度查询,例如:
(1)geo_distance
(2)geo_bounding_box
5、复合(compound)查询:将上述各种查询条件组合起来,合并查询条件,例如:
(1)bool
(2)function_score

基本语法:

GET /indexName/_search
{"query": {"查询类型": {"查询条件": "条件值"}}
}

如果是查询所有,那么就没有查询的条件,例如:

GET /hotel/_search
{"query": {"match_all": {}}
}

不过这种查询方法,最终显示的结果可能不会全部出来,避免压力过大,至于如何全部搜索出来,后续演示一下分页查询就好了。

全文检索查询

全文检索查询,会对用户输入的内容分词,常用于搜索框搜索:
match查询是全文检索查询的一种,会对用户输入内容分词,然后去倒排索引库检索,例如:

# 将外滩如家分词为外滩和如家进行检索,都包含的酒店排名最高
GET /hotel/_search
{"query": {"match": {"all": "外滩如家"}}
}

multi_match与match相似,但是允许查询多个字段:

# 查询酒店的品牌和名称是否与“外滩如家”匹配
GET /hotel/_search
{"query": {"multi_match": {"query": "外滩如家","fields": ["brand", "name"]}}
}

更推荐使用match,要查询的字段之前就已经全部放在all里面了。而multi_match要查询的字段太多,效率会更低下。

精确查询

精确查询一般是查找keyword、数值、日期、boolean等类型字段,不会对搜索条件做分词。常见的2种:
(1)term:根据词条精确值查询

GET /hotel/_search
{"query": {"term": {"city": {"value": "上海"}}}
}

(2)range:根据值的范围查询

# 查询 100<价格<=300 的酒店
GET /hotel/_search
{"query": {"range": {"price": {"gt": 100,"lte": 300}}}
}

地理查询

根据经纬度查询。常见应用场景包括携程、滴滴、微信等。
geo_bounding_box:选取两个经纬度坐标,并且根据这两个点做矩形,在矩形之内的酒店即为查询结果,比较适合用来查询一定范围内的信息。
geo_distance:查询到指定中心点小于某个距离值的所有文档。

GET /hotel/_search
{"query": {"geo_distance": {"distance": "15km","location": "31.21, 121.5"}}
}

复合查询

复合查询就是把其它查询组合起来,实现更复杂的搜素逻辑

相关性算分

function score:算分函数查询,可以控制文档相关性算分,控制文档排名。如百度竞价。
简单的算分可以直接算词条的频率:
T F (词条频率) = 词条出现次数 文档中词条总数 TF(词条频率)=\frac{词条出现次数}{文档中词条总数} TF(词条频率)=文档中词条总数词条出现次数
但是当搜索内容里面包括多个词条时,词条就有权重之分了,使用TF-IDF算法
I D F (逆文档频率) = L o g ( 文档总数 包含词条的文档总数 ) s c o r e = ∑ i n T F (词条频率) ∗ I D F (逆文档频率) IDF(逆文档频率)=Log(\frac{文档总数}{包含词条的文档总数})\\ score=\sum_i^nTF(词条频率) * IDF(逆文档频率) IDF(逆文档频率)=Log(包含词条的文档总数文档总数)score=inTF(词条频率)IDF(逆文档频率)
也就是说,这个词条在全部文档中出现的越多,它就越不值钱
当然,现在的ES已经不使用这种算法了,而采用了BM25算法
S c o r e ( Q , d ) = ∑ i n l o g ( 1 + N − n + 0.5 n + 0.5 ) ⋅ f i f i + k 1 ⋅ ( 1 − b + b ∗ d l a v g d l ) Score(Q,d) = \sum_i^nlog(1+\frac{N-n+0.5}{n+0.5}) · \frac{f_i}{f_i+k_1 · (1-b+b*\frac{dl}{avgdl})} Score(Q,d)=inlog(1+n+0.5Nn+0.5)fi+k1(1b+bavgdldl)fi
这个算法具体是怎么样更优秀的大家可以自行推导,看起来复杂但是其实也没有特别的复杂,比起TF-IDF算法,BM25算法受大量词频的影响会小很多,在大量词频的情况下也相对更平滑:
在这里插入图片描述
因此需要记住ES中的相关性打分的算法有哪些,我看一些大厂面试也是会考的,甚至上面的公式也是要会的。

TF-IDF:在ES5.0之前,会随着词频增加而越来越大
BM25:在ES5.0之后,会随着词频的增加而增大,但增长曲线会趋于水平

Function Score Query

使用function score query,可以修改文档的相关性算分(从原有的相关性算法基础上修改),根据新得到的算分排序。
这里直接用例子来进行说明,假设用户要搜索带着“外滩”的酒店,但是因为品牌方为“如家”的酒店跟我是合作关系,我当然就希望查询结果中带“如家”的排名会靠前一点:
在这里插入图片描述
这只是个例子,其使用还有多种重新算分的方法,需要掌握如下几点:

1、query:原始查询,搜索文档并根据相关性来打分(BM25算法),得到query score
2、filter:过滤条件,符合条件的文档才会被重新算分
3、weight:算法函数,算分函数的结果成为function score,将来会与query score运算,得到新算分,常见算分函数:
(1)weight:给一个常量值,作为function score
(2)field_value_factor:将文档中的某个字段值,作为function score
(3)random_score:随机生成一个值,作为function score
(4)script_score:自定义计算公式,公式结果作为function score
4、boost_mode:加权模式,定义query scorefunction score的运算方式:
(1)multiply:默认方式,相乘
(2)replace:用function score替换query score
(3)其他:sum、avg、max、min

总结:

function score query定义的三要素:
(1)过滤条件:决定哪些文档要加分
(2)算法函数:如何计算function score
(3)加权方式:function score与query score如何运算

Boolean Query

布尔查询与function score query不一样,function score query是在原来的算分基础上修改算分。而Boolean Query不会修改算分是一个或多个查询子句的组合。子查询的组合方式有:

must:必须匹配每个子查询,类似“与”
should:选择性匹配子查询,类似“或”
must_not:必须不匹配,不参与算分,类似“非”
filter:必须匹配,不参与算分

must_not和filter可以解决一个问题,子查询过多的时候,参与算分太多就会影响性能,而must_not和filter只会返回匹配和不匹配,却不去具体算分,同时因为几乎没有啥运算,所以ES底层会将其放到缓存中去,因此这两种方法会大大提升性能。例如用户要过滤出酒店价格低于500的,那么只需要将符合条件的呈现就行,没必要去再给价格算分后排个序。

这样的方法常见于搜索中下的筛选按钮,比如筛选出品牌、酒店的星级等(filter或must_not),高效率的先筛选出一部分符合条件的酒店,然后再去搜索框中搜索(must),从而提高整体效率。

例如:搜索名字包含“如家”,价格不高于400,在坐标31.21,121.5周围10km范围内的酒店。
在这里插入图片描述

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

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

相关文章

Chain-of-Thought Prompting Elicits Reasoning in Large Language Models导读

通过生成一系列中间推理步骤&#xff08;即“思维链”&#xff09;显著提高大型语言模型进行复杂推理的能力 这篇论文探讨了如何通过生成一系列中间推理步骤&#xff08;即“思维链”&#xff09;显著提高大型语言模型进行复杂推理的能力。研究人员使用一种简单的方法——思维…

vue项目如何打包,java项目如何打包

目录 vue项目如何打包 java项目如何打jar包 使用Maven打包为JAR&#xff08;方式一&#xff09;视图&#xff1a; 先双击clean再双击package即可打包 使用Maven打包为JAR&#xff08;方式二&#xff09;命令&#xff1a; 1、确保你已经安装了Maven&#xff0c;并且配置了相应…

通俗易懂理解小波池化以及WaveCNet网络模型

重要说明&#xff1a;本文从网上资料整理而来&#xff0c;仅记录博主学习相关知识点的过程&#xff0c;侵删。 一、参考资料 github代码&#xff1a;WaveCNet 小波变换和曲波变换用于池化层 通俗易懂理解小波变换(Wavelet Transform) 二、相关介绍 关于小波变换的详细介绍…

pdf.js 实现pdf在线搜索,分页,下载,放大,打印功能

下载插件地址&#xff1a; https://download.csdn.net/download/xiaogg3678/88780912 浏览器在线预览地址&#xff1a; http://localhost/pdfjs-viewer/web/viewer.html?filehttp://localhost/pdfjs-viewer/web/compressed.tracemonkey-pldi-09.pdf

springboot快速写接口

1. 建proj形式 name会变成文件夹的名字&#xff0c;相当于你的项目名称 基础包 2. 基础依赖 3. 配置数据库 这里要打开mysql&#xff0c;并且创建数据库 方法&#xff1a; 安装好数据库&#xff0c;改好账号密码用navicat来建表和账号配置properties.yml文件即可 4.用res…

C语言之指针的地址和指向的内容总结(八十四)

简介&#xff1a; CSDN博客专家&#xff0c;专注Android/Linux系统&#xff0c;分享多mic语音方案、音视频、编解码等技术&#xff0c;与大家一起成长&#xff01; 优质专栏&#xff1a;Audio工程师进阶系列【原创干货持续更新中……】&#x1f680; 优质专栏&#xff1a;多媒…

分布式因果推断在美团履约平台的探索与实践

美团履约平台技术部在因果推断领域持续的探索和实践中&#xff0c;自研了一系列分布式的工具。本文重点介绍了分布式因果树算法的实现&#xff0c;并系统地阐述如何设计实现一种分布式因果树算法&#xff0c;以及因果效应评估方面qini_curve/qini_score的不足与应对技巧。希望能…

Discuz论坛搭建:Linux宝塔面板一键部署,固定地址畅享公网访问

&#x1f308;个人主页&#xff1a;聆风吟 &#x1f525;系列专栏&#xff1a;网络奇遇记、Cpolar杂谈 &#x1f516;少年有梦不应止于心动&#xff0c;更要付诸行动。 文章目录 &#x1f4cb;前言一. 安装基础环境二. 一键部署Discuz三. 安装cpolar工具四. 配置域名访问Discuz…

ST-Link调试器:功能、用途和引脚

ST-Link调试器&#xff1a;功能、用途和引脚 介绍 在嵌入式系统开发中&#xff0c;调试器是一种至关重要的工具&#xff0c;它允许开发人员调试和编程微控制器&#xff0c;以确保系统正常运行并解决潜在的问题。ST-Link是STMicroelectronics公司推出的一款强大的调试器&#x…

【JaveWeb教程】(30)SpringBootWeb案例之《智能学习辅助系统》的详细实现步骤与代码示例(3)员工管理的实现

目录 SpringBootWeb案例033. 员工管理3.1 分页查询3.1.1 基础分页3.1.1.1 需求分析3.1.1.2 接口文档3.1.1.3 思路分析3.1.1.4 功能开发3.1.1.5 功能测试3.1.1.6 前后端联调 3.1.2 分页插件3.1.2.1 介绍3.1.2.2 代码实现3.1.2.3 测试 3.2 分页查询(带条件)3.2.1 需求3.2.2 思路分…

学习PyQt5

1、布局之后&#xff0c;无法移动对象到指定区域&#xff0c;无法改变对象大小。 原因&#xff1a;因为CtrlA选中了整个窗口&#xff0c;然后布局的时候就相当于整个窗口都按照这种布局&#xff0c;如选了水平布局&#xff0c;按钮一直在中间&#xff0c;无法拖到其它位置。 解…

华为三层交换机之基本操作

Telnet简介 Telnet是一个应用层协议,可以在Internet上或局域网上使用。它提供了基于文本的远程终端接口&#xff0c;允许用户在本地计算机上登录到远程计算机&#xff0c;然后像在本地计算机上一样使用远程计算机的资源。Telnet客户端和服务器之间的通信是通过Telnet协议进行的…