1. ホーム
  2. elasticsearch

[解決済み] ElasticSearchで単語の一部を検索する方法

2022-05-30 05:25:01

質問

最近ElasticSearchを使い始めたのですが、単語の一部を検索させることができないようです。

例 私のcouchdbから3つのドキュメントがElasticSearchにインデックスされています。

{
  "_id" : "1",
  "name" : "John Doeman",
  "function" : "Janitor"
}
{
  "_id" : "2",
  "name" : "Jane Doewoman",
  "function" : "Teacher"
}
{
  "_id" : "3",
  "name" : "Jimmy Jackal",
  "function" : "Student"
} 

そこで今度は、"Doe" を含むすべてのドキュメントを検索したいと思います。

curl http://localhost:9200/my_idx/my_type/_search?q=Doe

これでは何もヒットしません。しかし、もし私が

curl http://localhost:9200/my_idx/my_type/_search?q=Doeman

これは1つのドキュメント(John Doeman)を返します。

インデックスのプロパティとして、異なる分析器と異なるフィルタを設定してみました。また、完全なクエリ (たとえば。

{
  "query": {
    "term": {
      "name": "Doe"
    }
  }
}

) しかし、何も動作しないようです。

ElasticSearchで"Doe"を検索したときに、John DoemanとJane Doewomanの両方を見つけるようにするにはどうしたらよいでしょうか?

UPDATE

Igorが提案したように、nGramのtokenizerとfilterを使って、こんな風にやってみました。

{
  "index": {
    "index": "my_idx",
    "type": "my_type",
    "bulk_size": "100",
    "bulk_timeout": "10ms",
    "analysis": {
      "analyzer": {
        "my_analyzer": {
          "type": "custom",
          "tokenizer": "my_ngram_tokenizer",
          "filter": [
            "my_ngram_filter"
          ]
        }
      },
      "filter": {
        "my_ngram_filter": {
          "type": "nGram",
          "min_gram": 1,
          "max_gram": 1
        }
      },
      "tokenizer": {
        "my_ngram_tokenizer": {
          "type": "nGram",
          "min_gram": 1,
          "max_gram": 1
        }
      }
    }
  }
}

今抱えている問題は、一つ一つのクエリが全てのドキュメントを返してしまうことです。 何かポインターはありますか?nGramの使用に関するElasticSearchのドキュメントはあまり良くありません...。

どうすれば解決できますか?

私もnGramを使用しています。標準のトークナイザーを使い、nGramはフィルターとして使っています。以下は、私の設定です。

{
  "index": {
    "index": "my_idx",
    "type": "my_type",
    "analysis": {
      "index_analyzer": {
        "my_index_analyzer": {
          "type": "custom",
          "tokenizer": "standard",
          "filter": [
            "lowercase",
            "mynGram"
          ]
        }
      },
      "search_analyzer": {
        "my_search_analyzer": {
          "type": "custom",
          "tokenizer": "standard",
          "filter": [
            "standard",
            "lowercase",
            "mynGram"
          ]
        }
      },
      "filter": {
        "mynGram": {
          "type": "nGram",
          "min_gram": 2,
          "max_gram": 50
        }
      }
    }
  }
}

50文字までの単語を検索することができる。max_gramは必要に応じて調整してください。ドイツ語では単語が非常に大きくなることがあるので、高い値に設定しました。