如何通过Shingle分词实现Elasticsearch多词关键词精准匹配?
解决方案
要实现搜索文本中的完整短语匹配keywords字段里的多词关键词,你需要创建一个自定义Shingle分析器,仅在查询阶段处理输入文本,生成多词短语Token后再去匹配keyword类型的keywords字段。
步骤1:添加自定义Shingle分析器到索引设置
给food-suggestion索引添加自定义分析器,用于在查询时生成2词短语Token:
PUT /food-suggestion/_settings { "analysis": { "analyzer": { "shingle_analyzer": { "tokenizer": "standard", "filter": [ "lowercase", "shingle_filter" ] } }, "filter": { "shingle_filter": { "type": "shingle", "min_shingle_size": 2, "max_shingle_size": 2, "output_unigrams": false // 仅生成2词短语,不保留单个词,确保只有完整短语匹配 } } } }
- 若需要同时支持单个词(如
cheesecake)和短语匹配,将output_unigrams设为true即可,分析器会同时生成单个词和短语Token。
步骤2:修改查询语句使用自定义分析器
更新查询,指定用shingle_analyzer处理输入文本,自动从输入中提取多词短语,匹配keywords字段的完整关键词:
GET /food-suggestion/_search { "query": { "bool": { "must": [ { "match": { "keywords": { "query": "Today I have eaten a cinnamon roll", "analyzer": "shingle_analyzer", "operator": "or" } } } ], "filter": [ { "term": { "languageId": 1 } }, { "term": { "webId": 2 } } ] } } }
原理说明
原查询使用standard分析器会将输入文本拆分为单个词(如cinnamon、roll),但keywords字段是keyword类型,存储的是完整的多词字符串(如cinnamon roll),单个词无法匹配完整字符串。
自定义Shingle分析器会将输入文本处理为连续的2词短语Token(如today i、cinnamon roll等),这些短语Token可以直接匹配keywords字段中存储的完整关键词,从而实现精准的短语匹配需求。
内容的提问来源于stack exchange,提问作者josep lluis marin trabalon
相关产品推荐
相关产品推荐

