Elasticsearch之模糊查询

本文深入解析Elasticsearch中的模糊查询技术,包括前缀查询、通配符查询及正则查询,详细阐述了不同查询方式的工作原理、性能对比及应用场景,特别强调了在text与keyword字段类型上的区别。

前言

模糊查询主要针对文本类型使用。
1、当搜索字段是text类型时:由于它会分词,在执行wildcard、regexp、prefix时和es会检查字段中的每个词条,而不是整个字段。
2、当搜索字段是keyword类型时:在执行wildcard、regexp、prefix时和es会检查字段中整个文本。

性能方面:prefix > wildcard > regexp

1、模糊查询之前缀查询-prefix

prefix 前缀查询,以下查询示例 表示查出所有姓张的人(名字name以张开头),并且只返回name字段(_source字段的列表就是需要返回的)
查询示例:

POST /_search?pretty
{
    "query":{
        "bool":{
            "filter":[{"prefix":{"name":"张"}}                              
            ]}},
"size": 5,
"_source": ["name"]
}

2、模糊查询之通配符查询-wildcard

wildcard支持shell标准通配符。
注意:字母要小写!
注意:字母要小写!
注意:字母要小写!

通配符含义实例
*匹配 0 或多个字符a*b,a与b之间可以有任意长度的任意字符, 也可以一个也没有, 如 aabcb, axyzb, a012b, ab
?匹配任意单个字符a?b,a与b之间有且只有一个字符, 可以是任意字符, 如 aab, abb, acb, a0b
[list]匹配 list 中的任意单个字符a[xyz]b,a与b之间必须也只能有一个字符, 但只能是 x 或 y 或 z, 如 axb, ayb, azb。
[!list]匹配除 list 中的任意单一字符a[!0-9]b,a与b之间必须也只能有一个字符, 但不能是阿拉伯数字, 如 axb, aab, a-b。
[c1-c2]匹配 c1-c2 中的任意单一字符a[0-9]b,匹配0与9之间其中一个字符,如 a0b, a1b… a9b
{s1,s2,…}匹配 s1 或 s2 (或更多)中的一个字符串a{abc,xyz,123}b,a与b之间只能是abc或xyz或123这三个字符串之一

查询示例,查询名字中带有‘万’字的文档

POST /_search?pretty
{
    "query":{"bool":{
                       "filter":[{"wildcard":{"name":"*万*"}}                              
        ]}},
    "size": 2,
    "_source": ["name"]
}

3、模糊查询之正则查询-regexp

注意:字母要小写!
注意:字母要小写!
注意:字母要小写!
支持标准的正则。
查询示例:

POST /_search?pretty
{
  "query":{"bool":{
                       "filter":[{"regexp":{"name":".*张.*"}}                              
 ]}},
"size": 2,
"_source": ["name"]
}
Elasticsearch 中,模糊查询是一种非常强大的功能,它允许用户通过不完全匹配的方式检索数据。这种能力对于构建灵活的搜索体验至关重要。以下是实现模糊查询的一些方法和技术指南。 ### 模糊查询的基本概念 模糊查询基于编辑距离算法(Levenshtein Distance),它可以确定两个字符串之间的差异程度。Elasticsearch 使用这个概念来查找与给定关键词相似但不完全相同的文档。默认情况下,`fuzziness` 参数设置为 `AUTO`,这意味着 Elasticsearch 会自动根据词项长度选择合适的编辑距离阈值 [^1]。 ### 使用 Kibana 进行基本的模糊查询 你可以使用 Kibana 的 Dev Tools 来执行一个简单的模糊查询。下面是一个例子,展示如何对某个字段进行模糊查询: ```json GET /_search { "query": { "match": { "message": { "query": "quick brown fox", "fuzziness": "AUTO" } } } } ``` 在这个示例中,`message` 字段将被用来进行模糊匹配,而 `"fuzziness": "AUTO"` 表示让 Elasticsearch 自动决定最佳的模糊级别 [^1]。 ### 高亮显示匹配内容 当你执行模糊查询时,通常希望高亮显示匹配的部分以便于用户识别。可以通过添加 `highlight` 参数来实现这一点: ```json GET /_search { "query": { "match": { "content": { "query": "elasticsearch", "fuzziness": "AUTO" } } }, "highlight": { "fields": { "*": {} } } } ``` 这段代码不仅执行了模糊查询,还启用了高亮功能,使得所有匹配的结果中的相关部分都会被突出显示 [^1]。 ### 利用 Spring Data Elasticsearch 实现模糊查询 如果你正在使用 Java 并且利用 Spring Boot 框架,那么可以借助 Spring Data Elasticsearch 提供的抽象层来简化开发过程。例如,定义一个仓库接口如下所示即可支持模糊查询: ```java public interface BookRepository extends ElasticsearchRepository<Book, String> { List<Book> findByNameContaining(String keyword); } ``` 这里 `findByNameContaining` 方法就支持了基于名称字段的模糊搜索 [^2]。 ### 多字段索引以支持精确和模糊查询 为了同时支持某一字段上的精确查询和模糊查询,可以在映射(mapping)时配置该字段为 `multi_field` 类型。这样就可以分别指定不同的分析器用于不同类型的查询需求: ```json "properties": { "source.strain": { "type": "text", "fields": { "keyword": { "type": "keyword", "ignore_above": 256 } } } } ``` 上述配置中,`source.strain` 被定义为文本类型并应用了标准分析器,适合做模糊查询;而其子字段 `keyword` 则是未经过分析的原始字符串,适用于精确查询 [^3]。 ### 使用通配符查询实现模糊效果 除了直接使用 `match` 查询外,还可以考虑采用 `wildcard` 查询来达到类似的效果。这种方法特别适用于那些不需要分词处理的情况: ```json POST /indexname/_search { "query": { "wildcard": { "fieldname": { "value": "*value" } } } } ``` 此例中的 `wildcard` 查询允许你使用星号(`*`)作为通配符来进行模式匹配,从而实现一种形式上的“模糊”查询 [^4]。 ---
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值