Elasticsearch: Différence entre "Terme", "Expression de correspondance" et "Chaîne de requête"


116

Nouveau ici pour Elasticsearch et essayant de mieux comprendre la différence entre ces requêtes. Pour autant que je sache, termcorrespond à un seul terme (doit être en minuscules pour que la correspondance fonctionne?), Et les deux match phraseet query stringcorrespond à une chaîne de texte.

Réponses:


226

termla requête correspond à un seul terme tel quel: la valeur n'est pas analysée . Ainsi, il n'est pas nécessaire de le mettre en minuscules en fonction de ce que vous avez indexé.

Si vous avez fourni Bennettau moment de l'indexation et que la valeur n'est pas analysée, la requête suivante ne retournera rien:

{
  "query": {
    "term" : { "user" : "bennett" }
  }
}

match_phrase query analysera l'entrée si des analyseurs sont définis pour le champ interrogé et trouvera les documents correspondant aux critères suivants:

  • tous les termes doivent apparaître dans le champ
  • ils doivent avoir le même ordre que la valeur d'entrée

Par exemple, si vous indexez les documents suivants (en utilisant l' standardanalyseur pour le champ foo):

{ "foo":"I just said hello world" }

{ "foo":"Hello world" }

{ "foo":"World Hello" }

Cette match_phraserequête ne renverra que les premier et deuxième documents:

{
  "query": {
    "match_phrase": {
      "foo": "Hello World"
    }
  }
}

query_stringrecherche par requête, par défaut, sur un champ _all qui contient le texte de plusieurs champs de texte à la fois. En plus de cela, il est analysé et prend en charge certains opérateurs (ET / OU ...), les caractères génériques, etc. (voir la syntaxe associée ).

Au fur et à mesure des match_phraserequêtes, l'entrée est analysée en fonction de l'analyseur défini sur le champ interrogé.

Contrairement à match_phrase, les termes obtenus après analyse ne doivent pas nécessairement être dans le même ordre, sauf si l'utilisateur a utilisé des guillemets autour de l'entrée.

Par exemple, en utilisant les mêmes documents qu'auparavant, cette requête renverra tous les documents:

{
  "query": {
    "query_string": {
      "query": "hello World"
    }
  }
}

Mais cette requête renverra les 2 mêmes documents que la match_phraserequête:

{
  "query": {
    "query_string": {
      "query": "\"Hello World\""
    }
  }
}

Il y a beaucoup plus à dire sur les différentes options pour ces requêtes, veuillez consulter la documentation associée:

J'espère que cela est assez clair et que cela aidera.


Explication géniale, merveilleuse et approfondie! La seule chose sur laquelle je ne sais pas, c'est ce qu'est ou fait exactement une analyse ...
blee908

1
Vous êtes les bienvenus :) Les analyseurs traitent le texte afin d'obtenir les termes qui sont finalement indexés / recherchés. Lisez ces pages du Guide définitif d'ElasticSearch car il s'agit d'un concept très important à comprendre.
ThomasC

1
Ouais venant de SQL, il y a beaucoup de nouvelles idées ici. La différence entre les requêtes et les filtres, les valeurs exactes et le texte intégral, l'objet de recherche JSON et la manière dont la recherche élastique exécute sa recherche. Tellement à prendre !!! Merci pour la ressource!
blee908

1
@ThomasC Si vous aviez {"foo": "Hello beautiful world"} dans votre index, la requête de correspondance retournera-t-elle ceci?
batmaci

1
@batmaci une matchrequête utilise l'analyseur si le champ est analysé, donc oui. Par défaut, il renverra les documents ayant au moins un des termes (voir paramètre operator) et l'ordre n'est pas important.
ThomasC

17

Je pense que quelqu'un cherche définitivement des différences entre eux en ce qui concerne la RECHERCHE PARTIELLE Voici mon analyse avec 'analyseur standard' par défaut : -

Supposons que nous ayons des données: -

{"name": "Hello"}

Maintenant, que faire si nous voulons faire une recherche partielle avec ell ???

Requête de terme OU requête de correspondance

{"term":{"name": "*ell*" }

Ne fonctionnera pas, retournez en notant.

{"term":{"name": "*zz* *ell*" }

Ne fonctionnera pas, retournez en notant.

Conclusion - Le terme ou la correspondance ne peut pas du tout effectuer de recherche partielle

Requête générique: -

{"wildcard":{"name": "*ell*" }

Fonctionnera donner le résultat {"name": "Hello"}

{"wildcard":{"name": "*zz* *ell*" }

Ne fonctionnera pas, retournez en notant.

Conclusion - wildcard est capable de faire une recherche partielle avec un seul jeton

Chaîne de requête :-

{"query_string": {"default_field": "name","query": "*ell*"}

Fonctionnera donner le résultat {"name": "Hello"}

{"query_string": {"default_field": "name","query": "*zz* *ell*" }

Fonctionnera donner le résultat {"name": "Hello"}.

Conclusion - query_string est capable de rechercher avec deux jetons sont donnés

-> ici les jetons sont ell et zz


wildcard is able to do partial search with one token only: plus précisément, les wildcardrequêtes par défaut ne fonctionnent que sur les keywordchamps , qui sont par définition à jeton unique. Cela n'a rien à voir avec le contenu du champ contenant plus d'un mot. Dans votre requête générique, "ozzy hello" correspondrait.
sox avec Monica le
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.