2013-05-23 12 views
10

die Suche nach Namen (Text) mit Leerzeichen darin, was Problem zu mir, Ich habe Abbildung ähnlich wieSuche nach Namen (Text) mit Leerzeichen in Elasticsearch

"{"user":{"properties":{"name":{"type":"string"}}}}" 

Im Idealfall, was es zurückgeben und Rang Ergebnisse soll wie folgt

1) Bring on top names that exact match the search term (highest score) 
2) Names that starts with the search term (high score) 
3) Names that contains the exact search term as substring (medium score) 
4) Names that contains any of the search term token (lowest score) 

Beispiel für Namen in Elasticsearch folgenden

Maaz Tariq 
Ahmed Maaz Tariq 
Maaz Sheeba 
Maaz Bin Tariq 
Sana Tariq 
Maaz Tariq Ahmed 

Suche nach „Maaz Tariq“ sollten Ergebnisse

Maaz Tariq (highest score) 
Maaz Tariq Ahmed (high score) 
Ahmed Maaz Tariq (medium score) 
Maaz Bin Tariq (lowest score) 
Maaz Sheeba (lowest score) 
Sana Tariq (lowest score) 

in folgenden Reihenfolge sein Kann mich jemand zeigen, wie und welche zu verwenden Analysatoren? und wie ordnen Sie die Suchergebnisse für Namen ein?

Antwort

8

Sie können das multi field type, ein bool query und das custom boost factor query verwenden, um dieses Problem zu lösen.

Mapping:

{ 
    "mappings" : { 
     "user" : {   
      "properties" : { 
       "name": { 
        "type": "multi_field", 
        "fields": { 
         "name": { "type" : "string", "index": "analyzed" }, 
         "exact": { "type" : "string", "index": "not_analyzed" } 
        } 
       } 
      } 
     } 
    } 
} 

Abfrage:

{ 
    "query": { 
     "bool": { 
      "must": [ 
       { 
        "match": { 
         "name": "Maaz Tariq" 
        } 
       } 
      ], 
      "should": [ 
       { 
        "custom_boost_factor": { 
         "query": { 
          "term": { 
           "name.exact": "Maaz Tariq" 
          } 
         }, 
         "boost_factor": 15 
        } 
       }, 
       { 
        "custom_boost_factor": { 
         "query": { 
          "prefix": { 
           "name.exact": "Maaz Tariq" 
          } 
         }, 
         "boost_factor": 10 
        } 
       }, 
       { 
        "custom_boost_factor": { 
         "query": { 
          "match_phrase": { 
           "name": { 
            "query": "Maaz Tariq", 
            "slop": 0 
           } 
          } 
         }, 
         "boost_factor": 5 
        } 
       } 
      ] 
     } 
    } 
} 

edit:

Wie javanna darauf hingewiesen wird die custom_boost_factor nicht benötigt.

Abfrage ohne custom_boost_factor:

{ 
    "query": { 
     "bool": { 
      "must": [ 
       { 
        "match": { 
         "name": "Maaz Tariq" 
        } 
       } 
      ], 
      "should": [ 
       { 
        "term": { 
         "name.exact": { 
          "value": "Maaz Tariq", 
          "boost": 15 
         } 
        } 
       }, 
       { 
        "prefix": { 
         "name.exact": { 
          "value": "Maaz Tariq", 
          "boost": 10 
         } 
        } 
       }, 
       { 
        "match_phrase": { 
         "name": { 
          "query": "Maaz Tariq", 
          "slop": 0, 
          "boost": 5 
         } 
        } 
       } 
      ] 
     } 
    } 
} 
+0

würde ich bevorzugen eine filterbasierte Lösung, aber ich konnte den richtigen Filter für die 3. Anforderung nicht finden. – Ivaldi

+0

Sie können nur eine Phrase Abfrage dafür machen. Außerdem verstehe ich nicht, warum Sie eine custom_boost_factor-Abfrage benötigen. Können Sie Ihren verschiedenen Anfragen nicht einfach ein anderes Gewicht geben, indem Sie die "Boost" -Option verwenden? – javanna

+0

'Boost' ist in einer' sollte' Unterabfrage nicht erlaubt !? (Zumindest kenne ich die Syntax dafür nicht.) Und wie funktioniert ein Phrasenabfragefilter ohne die Abfrage 'span_near' und ohne die Abfrage' match_phrase'? – Ivaldi

0

Bei Java Api, wenn Quering genaue Strings mit Leerzeichen verwenden;

CLIENT.prepareSearch(index) 
    .setQuery(QueryBuilders.queryStringQuery(wordString) 
    .field(fieldName)); 

In vielen anderen Abfragen, erhalten Sie nichts als Ergebnis

Verwandte Themen