Elasticsearch高级检索之使用单个字母数字进行分词N-gram tokenizer(不区分大小写)【实战篇】
一、前言
小编最近在做到一个检索相关的需求,要求按照一个字段的每个字母或者数字进行检索,如果是不设置分词规则的话,英文是按照单词来进行分词的。
小编以7.6.0版本做的功能哈,大家可以根据自己的版本去官网看看,应该区别不大
例子:
C6153PE-冬日恋歌
,要可以通过任何一个数字和字母进行检索到,并且不区分大小写。c
,6
,c6
等等!
今天官网上有一些例子,觉得和实战还是有点区别,小编这里通过了测试抓紧来记录一下,希望帮助后来人哈!
二、测试分词策略
我们进入官网找到我们需要的策略:
Elasticsearch策略官网
N-gram 分词器
每当遇到指定字符列表中的一个时,ngram标记器首先将文本分解为单词,然后发出 指定长度的每个单词的N-gram。
N-gram 就像一个在单词上移动的滑动窗口——一个指定长度的连续字符序列
。它们对于查询不使用空格或复合词长的语言很有用。
我们去kibana
进行测试分词策略是否符合我们的要求:
POST _analyze
{
"tokenizer": "ngram",
"text": "C6153PE-冬日恋歌"
}
分词分得细,会导致检索的效率降低,但是需求如此,没办法,最重要的是小编这里的数据量只有1w,其实换了这种分词,是无感知的!
分词策略规则:
ngram分词器接受以下参数:
参数 | 解释 |
---|---|
min_gram | 以 gram 为单位的最小长度。默认为1. |
max_gram | 以 gram 为单位的最大字符长度。默认为2. |
token_chars | 应包含在令牌中的字符类,Elasticsearch 将根据不属于指定类的字符进行拆分。默认为[](保留所有字符)详细参数见下表 |
custom_token_chars | 应被视为令牌一部分的自定义字符。例如,将此设置为+-_将使标记器将加号、减号和下划线符号视为标记的一部分。 |
min_gram
将和设置max_gram
为相同的值通常是有意义的。长度越小,匹配的文档越多,但匹配的质量越低。长度越长,匹配越具体。三元组(长度3)是一个很好的起点。官方比较推荐使用3,可能是因为效率分词粒度两不误吧,这里不符合小编的,小编这里使用是1,2,也就是默认的值
token_chars参数 | 解释例子 |
---|---|
letter | 字母,例如a, b,ï或京 |
digit | 数字,例如3或7 |
whitespace | 空白,例如" "或"\n" |
punctuation | 标点,例如!或" |
symbol | 标记, 例如$或√ |
custom | 自定义,需要使用 custom_token_chars设置设置的自定义字符 |
custom_token_chars
:
应被视为令牌一部分的自定义字符。例如,将此设置为+-_将使标记器将加号、减号和下划线符号视为标记的一部分。
三、在索引字段中使用
官方是使用一个字段进行测试的,这里小编就直接使用公司的索引进行演示了!
这里是官网的例子:
下面放出来小编实战后的例子:
总结就是在settings
配置分词策略,在mappings
中进行使用即可!!
PUT /product
{
"settings": {
"number_of_shards": 1,
"number_of_replicas": 0,
"index": {
"max_result_window": 100000000
},
# 这里使用分词策略
"analysis": {
"analyzer": {
"my_analyzer": {
# 这里分词指定下面策略的具体配置的名称
"tokenizer": "my_tokenizer",
# 这里忽略大小写配置
"filter": [
"lowercase"
]
}
},
# 具体策略配置
"tokenizer": {
"my_tokenizer": {
"type": "ngram",
"min_gram": 1,
"max_gram": 2,
"token_chars": [
"letter",
"digit"
]
}
}
}
},
"mappings": {
"dynamic": "strict",
"properties": {
"@timestamp": {
"type": "date"
},
"@version": {
"type": "text",
"fields": {
"keyword": {
"type": "keyword",
"ignore_above": 256
}
}
},
"cargoNo": {
"type": "text"
},
"name": {
"type": "text"
},
"sort": {
"type": "integer"
},
"attribute13": {
"type": "text",
# 在需要的字段指定我们写的分词策略
"analyzer": "my_analyzer"
},
"isDeleted": {
"type": "integer"
}
}
}
}
四、在springboot中实战
为了公司,小编只粘贴部分条件构建规则:
SearchRequest searchRequest = new SearchRequest("product");
SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
BoolQueryBuilder bool = new BoolQueryBuilder();
BoolQueryBuilder boolQueryBuilder = new BoolQueryBuilder();
boolQueryBuilder.should(QueryBuilders.matchPhraseQuery("name", model))
.should(QueryBuilders.matchPhraseQuery("cargoNo", model))
.should(QueryBuilders.wildcardQuery("cargoNo", "*" + model + "*"))
// 我们分词规则的字段查询
.should(QueryBuilders.matchPhraseQuery("attribute13", model));
bool.must(boolQueryBuilder);
searchSourceBuilder.query(bool);
searchRequest.source(searchSourceBuilder);
我们拿着页面感受一下分词带来的效果:
效果实现,随便一个字母都可以查询出来,这里只显示名称和一个数字,其实是使用attribute13
来进行查询的,是因为attribute13
是名称的第一个-
之前的截出来的。
五、总结
这样我们就完成了一些定制化的需求,完美交差,还得是看官网啊!!一定要去看官网!搜了好多都没有这种的教程,写出来帮助后来人,但是详细的还得是看官网哈!小编这里也是把官网的一些概念写到了博客里!!
如果对你有帮助还请不要吝啬你的发财小手给小编来个一键三连哦!谢谢大家了!!
有缘人才可以看得到的哦!!!
Elasticsearch高级检索之使用单个字母数字进行分词N-gram tokenizer(不区分大小写)【实战篇】的更多相关文章
- ES 21 - Elasticsearch的高级检索语法 (包括term、prefix、wildcard、fuzzy、boost等)
目录 1 term query - 索引词检索 1.1 term query - 不分词检索 1.2 terms query - in检索 2 prefix query - 前缀检索 3 wildca ...
- Elasticsearch实现类Google高级检索
文章转载自: https://mp.weixin.qq.com/s?__biz=MzI2NDY1MTA3OQ==&mid=2247483914&idx=1&sn=436f814 ...
- Elasticsearch原理学习--为什么Elasticsearch/Lucene检索可以比MySQL快?
转载于:http://vlambda.com/wz_wvS2uI5VRn.html 同样都可以对数据构建索引并通过索引查询数据,为什么Lucene或基于Lucene的Elasticsearch会比关系 ...
- ElasticSearch高级查询
ElasticSearch高级查询 https://www.imooc.com/video/15759/0 ElasticSearch查询 1,子条件查询:特定字段查询所指特定值 1.1query c ...
- 对文本行进行排序,新增-d(目录排序),只对字母数字空格排序(TCPL 练习5-16)
文本行的排序用到了命令行参数以及多级指针,在要求只对字母数字空格进行排序时,关键的问题点是兼容-f命令参数,也就是排序的同时忽略大小写.由于在之前的练习中,我将忽略大小写的比较方法重新写了一个函数tr ...
- js 正则 以字母开头必须有 大小写字母数字组成 可以有“@"或 ”.“
js 正则 以字母开头必须有 大小写字母数字组成 可以有“@"或 ”.“ var reg = /^[a-zA-Z]{1}(?=.*[a-z])(?=.*[A-Z])[a-zA-Z\d_@ ...
- JS生成随机的由字母数字组合的字符串
前言 最近有个需求,是需要生成3-32位长度的字母数字组合的随机字符串,另一个是生成43位随机字符串. 方法一 奇妙的写法 1 Math.random().toString(36).substr( ...
- 计算机算法-C语言-统计字母数字个数解
Question:输入一串以“?”结尾的字符,分别统计其中字母数字的个数,输出字母及数字的个数. Solve: #include<stdio.h> #include<stdlib.h ...
- js随机生成字母数字组合的字符串 随机动画数字
效果描述: 附件中只有一个index.html文件有效 其中包含css以及html两部分内容 纯js生成的几个随机数字 每次都不重复,点击按钮后再次切换 使用方法: 1.将css样式引入到你的网页中 ...
随机推荐
- JDK的下载与安装和环境变量的配置
一.jdk下载打开浏览器在地址栏输入: http://www.oracle.com ,进入Oracle官网主页面,选择 Products-----Java---->Download Java . ...
- javaScript去重的11种方法
前言 去重是开发和面试中经常遇到的问题,下面是总结的 11 种去重方法 方法 示例数组 var arr = [1, 2, 4, 5, 5, 2, 1, 1, 4, 6] set + 解构赋值 这种方法 ...
- java -jar -Xbootclasspath/a:/xxx/config xxx .jar 和 java -jar xxx .jar 的区别
1.如果有用Xbootclasspath的话则config的文件会直接覆盖jar里面的resouces文件,覆盖application.yml ,也会覆盖logback-spring.xml ,比如j ...
- 面试官:你确定 Redis 是单线程的进程吗?
作者:小林coding 计算机八股文网站:https://xiaolincoding.com 大家好,我是小林. 这次主要分享 Redis 线程模型篇的面试题. Redis 是单线程吗? Redis ...
- Centos7借助docker部署mysql,提供远程链接服务
Centos7 借助docker部署mysql,并提供远程连接服务 安装docker 运行docker 注意安装docker和运行docker的步骤很简单,可以参考我学习docker的笔记 docke ...
- C#/VB.NET: 将Word或Excel文档转化为Text
Text文件只由纯文本内容组成,且没有格式,所以其大小比Word或Excel文件更小.除此之外,Text文件还具有跨平台性,几乎与所有应用程序都兼容.因此,在某些时候,我们可能需要将Word或Exce ...
- 基于图的深度优先搜索策略(耿7.10)--------西工大noj
代码 代码 #include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct ...
- 业务可视化-让你的流程图"Run"起来(3.分支选择&跨语言分布式运行节点)
前言 首先,感谢大家对上一篇文章[业务可视化-让你的流程图"Run"起来(2.问题与改进)]的支持. 分享一下近期我对这个项目的一些改进. 1. 增加了分支选择工程,可以根据节点的 ...
- Stream流中的常用方法foeEach和Stream流中的常用方法filter
延迟方法:返回值类型仍然是Stream接口自身类型的方法,因此支持链式调用.(除了中介方法外,其余方法均为延迟方法) 终结方法:返回值类型不再是Stream接口自身类型的方法,因此不再支持类似Stri ...
- 使用Python3.7结合Redisearch代替ElasticSearch实现的全文检索功能服务
原文转载自「刘悦的技术博客」https://v3u.cn/a_id_105 "检索"是很多产品中无法绕开的一个功能模块,当数据量小的时候可以使用模糊查询等操作凑合一下,但是当面临海 ...