首页 > 解决方案 > 如何在弹性搜索中查询单词的替代拼写和表示?

问题描述

我正在使用弹性搜索来查询theme文档中的字段。例如:

[
  { theme: 'landcover' },
  { theme: 'land cover' },
  { theme: 'land-cover' },
  etc
]

我想指定搜索landcover与所有这些文档匹配的术语。我该怎么做呢?

到目前为止,我已经尝试在match搜索中使用模糊运算符以及模糊查询。然而,这些方法似乎都不起作用,这让我感到惊讶,因为我对模糊搜索的理解是它们会提供一种不精确匹配的方法。

我错过了什么?从文档中我看到模糊性肯定会寻找搜索词的近似值:

在查询文本或关键字字段时,模糊性被解释为 Levenshtein 编辑距离——一个字符需要对一个字符串进行更改以使其与另一个字符串相同的次数。

我认为“土地覆盖”和“土地覆盖”很接近。不是这样吗?(这是我第一次听说 Levenshtein 编辑距离,所以我不知道额外/更少的字符在这个测量方面意味着什么)。

这似乎不起作用的匹配查询示例:

{
  query: {
    match: {
      'theme': {
        query: 'landcover'
        fuzziness: 'AUTO' // I've tried 2, '2', 6, '6', etc.
      },
    },
  },
}

// When the term is 'land-cover' and fuzziness is auto, then 'land cover' is matched. But 'landcover' is not

还有一个似乎不起作用的“模糊”查询示例:

{
  query: {
    fuzzy: {
      'theme': {
        value: query,
        fuzziness: 'AUTO', // Tried other values
      },
    },
  },
}

// When the term is 'land-cover' and fuzziness is auto, then 'landcover' is matched. But 'land cover' is not. So works almost opposite to the match query in this regard

(注意 - 这些查询被转换为 JSON 并运行并返回合理的结果,只是模糊性似乎不像我预期的那样工作)

环顾 StackOverflow,我看到一些问题似乎表明查询索引在某种程度上与索引的创建方式相关 - 即我不能只对任何已经存在的索引运行临时查询并期望结果。这个对吗?(对不起 - 我是弹性搜索的新手,我正在查询一个已经存在的索引)。

这个答案似乎相关(如何找到搜索词的近似匹配项):https ://stackoverflow.com/a/55772800/3114742 - 提到我应该在索引数据之前做一些称为“字段映射”的事情。但是示例查询不包括fuzziness运算符。因此,在这种情况下,我对模糊运算符的实际用途感到困惑。

标签: elasticsearchelasticsearch-query

解决方案


仔细查看文档,我发现以下内容:

Elasticsearch 使用“索引”而不是数据库的概念。但从熟悉 CouchDB 和 MongoDB(它们都是 JSON 存储)的人的角度来看,CouchDB 数据库和 Elasticsearch 索引之间肯定存在一些相似之处。尽管 elasticsearch 索引本身并不是一个权威的数据存储(它是从数据源“构建”的)。

例如,对于一个给定的索引,my-index. 您可以将 JSON 字符串(文档)插入my-indexPUTElasticsearch 中:

PUT /... '{... json string ...}'

JSON 字符串可以直接来自 JSON 存储(Mongo、Couch 等),也可以从各种来源拼凑而成。我猜。

Elasticsearch 将在插入时处理文档并附加到倒排树。对于文本字段,这意味着 K:V 对将从 JSON 文档文本创建,键是文本的片段,值是对在源(JSON 文档)中找到该文本片段的位置的引用。

换句话说,当将文档插入 Elasticsearch 索引时,会“分析”内容以创建添加到索引中的 K:V 对。

那么,我想,搜索 Elasticsearch 意味着查找作为索引中的键的搜索词,并将值(键的源)与搜索中定义的源(我认为)进行比较,然后返回源文档,其中特定字段存在搜索词。

所以:

  1. 在插入索引时分析文本
  2. 分析查询(使用与创建索引相同的分析器)

所以在我的例子中(如上所述),默认分析器足以创建允许基本模糊匹配的索引(即在匹配查询中,“土地覆盖”与“土地覆盖”匹配,在模糊查询中, "land-cover" 与 "landcover" 匹配——我不知道为什么这些匹配不同!)

但是为了改进搜索结果,我认为我需要在将文档插入索引时以及在解析查询以应用于索引时调整分析器/标记器。

我对分析/标记化的理解是,这是从源文档构建倒排索引的配置。即定义倒排索引的键是什么。据我所知,搜索索引没有什么魔力。搜索词必须与倒排索引中的键匹配,否则将没有结果。

我仍然不确定在这种情况下模糊实际上在做什么。

所以简而言之,查询弹性搜索似乎需要对源数据的索引方式和查询的设计方式有一个“整体的视角”。

但是,作为免责声明,我在弹性搜索经验不到一天的情况下并不是这个主题的权威答案,因此仍然会感谢更好的答案!


推荐阅读