【发布时间】:2017-12-09 13:17:33
【问题描述】:
是否可以告诉 ElasticSearch 使用所有克的“最佳匹配”而不是使用克作为同义词?
默认情况下,ElasticSearch 使用grams 作为同义词并返回匹配不佳的文档。最好用例子来展示,假设我们有两个人在索引中:
alice wang
sarah kerry
我们搜索ali12345:
{
query: {
bool: {
should: {
match: { name: 'ali12345' }
}
}
}
}
它会返回alice wang。
这怎么可能?因为默认情况下 ElasticSearch 使用grams 作为同义词,所以,即使只有一个gram 匹配 - 文档也会被匹配。
如果您检查查询,您会发现它将克视为同义词
...
"explanation": {
"value": 5.274891,
"description": "weight(Synonym(name: ali name:li1 name:i12 name:123 name:234 name:345 ) in 0) [PerFieldSimilarity], result of:",
...
我想知道是否可以告诉它使用“最佳匹配”查询,以实现类似:
{
query: {
bool: {
should: [
{ term: { body: 'ali' }},
{ term: { body: 'li1' }},
{ term: { body: 'i12' }},
{ term: { body: '123' }},
{ term: { body: '234' }},
{ term: { body: '345' }},
],
minimum_should_match: '75%'
}
}
}
问题:
当然可以手动生成此查询,但是您必须手动应用 ngram 解析和其他分析器管道。所以我想知道它是否可以由 ElasticSearch 完成?
当有几十克/词时,这种长字符串查询的性能如何?它是否会使用一些智能优化,例如搜索类似文档(请参阅
more_like_this) - 当它尝试不使用所有术语而只使用最高tf-idf的术语时?
附:
索引配置
{
mappings: {
object: {
properties: {
name: {
type: 'text',
analyzer: 'trigram_analyzer'
}
}
}
},
settings: {
analysis: {
filter: {
trigram_filter: { type: 'ngram', min_gram: 3, max_gram: 3 }
},
analyzer: {
trigram_analyzer: {
type: 'custom',
tokenizer: 'keyword',
filter: [ 'trigram_filter' ]
}
}
}
}
}
【问题讨论】:
-
你到底想做什么?您当前使用的
match查询方法有什么问题? -
@AndreiStefan 默认的
match将找到alice wang作为ali12345查询的匹配项。这显然是错误的。此外(虽然我不确定)相关性以类似的破坏方式计算。 -
它发现ali12345是因为ngrams。如果您不希望 ali12345 与 ngrams 匹配,那么呢?
-
它发现ali12345是因为ngrams。如果您不希望 ali12345 与 ngrams 匹配,那么呢?
-
@AndreiStefan 有很多方法可以使用 ngram。我想要类似于余弦相似度的东西。
标签: elasticsearch n-gram trigram