Correspondance de phrasesCompatible with Milvus 2.5.17+

La correspondance des phrases vous permet de rechercher des documents contenant les termes de votre requête sous la forme d'une phrase exacte. Par défaut, les mots doivent apparaître dans le même ordre et être directement adjacents les uns aux autres. Par exemple, une requête portant sur "robotics machine learning" aboutit à un texte du type "...typical robotics machine learning models...", où les mots "robotics", "machine" et "learning" apparaissent dans l'ordre, sans aucun autre mot entre eux.

Cependant, dans le monde réel, la correspondance stricte des phrases peut être trop rigide. Vous pourriez vouloir faire correspondre un texte comme "...des modèles d'apprentissage automatique largement adoptés en robotique...". Dans ce cas, les mêmes mots-clés sont présents, mais pas côte à côte ni dans l'ordre original. Pour gérer cette situation, la recherche de phrases prend en charge le paramètre slop, qui introduit une certaine flexibilité. La valeur slop définit le nombre de décalages positionnels autorisés entre les termes de la phrase. Par exemple, avec une valeur slop de 1, une requête pour "machine learning" peut correspondre à un texte comme "...machine deep learning...", où un mot ("deep") sépare les termes originaux.

Vue d'ensemble

Alimentée par la bibliothèque du moteur de recherche Tantivy, la correspondance de phrases fonctionne en analysant les informations relatives à la position des mots dans les documents. Le diagramme ci-dessous illustre le processus :

Phrase Match Workflow Flux de travail de la correspondance de phrases

  1. Tokenisation des documents: Lorsque vous insérez des documents dans Milvus, le texte est divisé en tokens (mots ou termes individuels) à l'aide d'un analyseur, les informations de position étant enregistrées pour chaque token. Par exemple, doc_1 est tokenisé en ["machine" (pos=0), "learning" (pos=1), "boosts" (pos=2), "efficiency" (pos=3)]. Pour plus d'informations sur les analyseurs, reportez-vous à la section Vue d'ensemble des analyseurs.

  2. Création d'un index inversé: Milvus crée un index inversé, en associant chaque mot clé au(x) document(s) dans le(s)quel(s) il apparaît et aux positions du mot clé dans ces documents.

  3. Correspondance des phrases: lorsqu'une requête de phrase est exécutée, Milvus recherche chaque token dans l'index inversé et vérifie leurs positions pour déterminer s'ils apparaissent dans l'ordre et la proximité corrects. Le paramètre slop contrôle le nombre maximum de positions autorisées entre les mots correspondants :

    • slop = 0 signifie que les mots doivent apparaître dans l 'ordre exact et être immédiatement adjacents (c'est-à-dire sans mots supplémentaires entre eux).

      • Dans l'exemple, seul doc_1 ("machine" à pos=0, "learning" à pos=1) correspond exactement.
    • slop = 2 permet jusqu'à deux positions de flexibilité ou de réarrangement entre les mots correspondants.

      • Cela permet d'inverser l'ordre ("machine à apprendre") ou de laisser un petit espace entre les mots.

      • Par conséquent, les documents doc_1, doc_2 ("learning" à pos=0, "machine" à pos=1) et doc_3 ("learning" à pos=1, "machine" à pos=2) correspondent tous.

Activer la correspondance des phrases

La correspondance de phrases fonctionne avec le type de champ VARCHAR, le type de données de chaîne dans Milvus. Pour activer la correspondance des phrases, configurez votre schéma de collecte en définissant les paramètres enable_analyzer et enable_match sur True, comme pour la correspondance de texte.

Définissez enable_analyzer et enable_match

Pour activer la correspondance de phrases pour un champ VARCHAR spécifique, définissez les paramètres enable_analyzer et enable_match sur True lorsque vous définissez le schéma du champ. Cette configuration indique à Milvus de tokeniser le texte et de créer un index inversé avec les informations de position requises pour une correspondance de phrases efficace.

Voici un exemple de définition de schéma pour activer la correspondance de phrases :

from pymilvus import MilvusClient, DataType

# Create a schema for a new collection
schema = MilvusClient.create_schema(enable_dynamic_field=False)
schema.add_field(
    field_name="id",
    datatype=DataType.INT64,
    is_primary=True,
    auto_id=True
)
# Add a VARCHAR field configured for phrase matching
schema.add_field(
    field_name='text',                 # Name of the field
    datatype=DataType.VARCHAR,         # Field data type set as VARCHAR (string)
    max_length=1000,                   # Maximum length of the string
    enable_analyzer=True,              # Enables text analysis (tokenization)
    enable_match=True                  # Enables inverted indexing for phrase matching
)
schema.add_field(
    field_name="embeddings",
    datatype=DataType.FLOAT_VECTOR,
    dim=5
)

Facultatif : Configurer un analyseur

La précision de la correspondance des phrases dépend considérablement de l'analyseur utilisé pour tokeniser vos données textuelles. Différents analyseurs conviennent à différentes langues et à différents formats de texte, ce qui affecte la tokenisation et la précision de positionnement. La sélection d'un analyseur approprié pour votre cas d'utilisation spécifique permet d'optimiser les résultats de la recherche de phrases.

Par défaut, Milvus utilise l'analyseur standard, qui tokenise le texte en fonction des espaces blancs et de la ponctuation, supprime les tokens de plus de 40 caractères et convertit le texte en minuscules. Aucun paramètre supplémentaire n'est requis pour l'utilisation par défaut. Pour plus d'informations, reportez-vous à la section Analyseur standard.

Si votre application nécessite un analyseur spécifique, configurez-le à l'aide du paramètre analyzer_params. Par exemple, voici comment configurer l'analyseur english pour la recherche de phrases dans un texte anglais :

# Define analyzer parameters for English-language tokenization
analyzer_params = {
    "type": "english"
}

# Add the VARCHAR field with the English analyzer enabled
schema.add_field(
    field_name='text',                 # Name of the field
    datatype=DataType.VARCHAR,         # Field data type set as VARCHAR
    max_length=1000,                   # Maximum length of the string
    enable_analyzer=True,              # Enables text analysis
    analyzer_params=analyzer_params,   # Specifies the analyzer configuration
    enable_match=True                  # Enables inverted indexing for phrase matching
)

Milvus prend en charge plusieurs analyseurs adaptés à différentes langues et à différents cas d'utilisation. Pour plus d'informations, reportez-vous à la section Vue d'ensemble des analyseurs.

Utiliser la correspondance de phrases

Une fois que vous avez activé la correspondance pour un champ VARCHAR dans votre schéma de collecte, vous pouvez effectuer des correspondances de phrases à l'aide de l'expression PHRASE_MATCH.

L'expression PHRASE_MATCH n'est pas sensible à la casse. Vous pouvez utiliser PHRASE_MATCH ou phrase_match.

Syntaxe de l'expression PHRASE_MATCH

Utilisez l'expression PHRASE_MATCH pour spécifier le champ, l'expression et la flexibilité facultative (slop) lors de la recherche. La syntaxe est la suivante :

PHRASE_MATCH(field_name, phrase, slop)
  • field_name: Le nom du champ VARCHAR sur lequel vous effectuez des recherches de phrases.

  • phrase: L'expression exacte à rechercher.

  • slop (facultatif): Un nombre entier spécifiant le nombre maximum de positions autorisées dans les éléments de correspondance.

    • 0 (par défaut) : Ne recherche que les expressions exactes. Exemple : Un filtre pour "machine learning" correspondra exactement à "machine learning", mais pas à "machine boosts learning" ou "learning machine".

    • 1: Permet des variations mineures, telles qu'un terme supplémentaire ou un changement mineur de position. Exemple : Un filtre pour "machine learning" correspondra à "machine boosts learning" (un jeton entre "machine" et "learning") mais pas à "learning machine" (termes inversés).

    • 2: Permet une plus grande flexibilité, y compris l'inversion de l'ordre des termes ou jusqu'à deux tokens entre eux. Exemple : Un filtre pour "machine learning" correspondra à "learning machine" (termes inversés) ou à "machine quickly boosts learning" (deux termes entre "machine" et "learning").

Exemple de jeu de données

Supposons que vous ayez une collection nommée tech_articles contenant les cinq entités suivantes :

doc_id

text

1

"L'apprentissage automatique renforce l'efficacité de l'analyse des données à grande échelle

2

"L'apprentissage d'une approche basée sur la machine est vital pour les progrès de l'IA moderne"

3

"Les architectures de machines d'apprentissage profond optimisent les charges de calcul

4

"La machine améliore rapidement les performances du modèle pour un apprentissage continu"

5

"L'apprentissage d'algorithmes avancés élargit les capacités de l'IA.

Requête avec correspondance de phrases

Lors de l'utilisation de la méthode query(), PHRASE_MATCH agit comme un filtre scalaire. Seuls les documents contenant l'expression spécifiée (sous réserve de la marge autorisée) sont renvoyés.

Exemple : slop = 0 (correspondance exacte)

Cet exemple renvoie les documents contenant l'expression exacte "machine learning" sans aucun token supplémentaire entre les deux.

# Match documents containing exactly "machine learning"
filter = "PHRASE_MATCH(text, 'machine learning')"

result = client.query(
    collection_name="tech_articles",
    filter=filter,
    output_fields=["id", "text"]
)

Résultats attendus :

doc_id

text

1

"L'apprentissage automatique améliore l'efficacité de l'analyse des données à grande échelle"

Seul le document 1 contient l'expression exacte " machine learning" dans l'ordre spécifié, sans aucun élément supplémentaire.

Recherche avec correspondance de phrases

Dans les opérations de recherche, PHRASE_MATCH est utilisé pour filtrer les documents avant d'appliquer le classement par similarité vectorielle. Cette approche en deux étapes permet d'abord de restreindre l'ensemble des candidats par la correspondance textuelle, puis de reclasser ces candidats sur la base de l'intégration vectorielle.

Exemple : slop = 1

Le filtre est appliqué aux documents qui contiennent l'expression "machine à apprendre" avec une légère flexibilité.

# Example: Filter documents containing "learning machine" with slop=1
filter_slop1 = "PHRASE_MATCH(text, 'learning machine', 1)"

result_slop1 = client.search(
    collection_name="tech_articles",
    anns_field="embeddings",
    data=[query_vector],
    filter=filter_slop1,
    search_params={"params": {"nprobe": 10}},
    limit=10,
    output_fields=["id", "text"]
)

Résultats de l'appariement :

doc_id

text

2

"L'apprentissage d'une approche basée sur la machine est vital pour les progrès de l'IA moderne"

3

"Les architectures de machines d'apprentissage en profondeur optimisent les charges de calcul.

5

"L'apprentissage d'algorithmes de machine avancés accroît les capacités de l'IA".

Exemple : slop = 2

Cet exemple autorise une pente de 2, ce qui signifie que jusqu'à deux tokens supplémentaires (ou termes inversés) sont autorisés entre les mots "machine" et "learning".

# Example: Filter documents containing "machine learning" with slop=2
filter_slop2 = "PHRASE_MATCH(text, 'machine learning', 2)"

result_slop2 = client.search(
    collection_name="tech_articles",
    anns_field="embeddings",             # Vector field name
    data=[query_vector],                 # Query vector
    filter=filter_slop2,                 # Filter expression
    search_params={"params": {"nprobe": 10}},
    limit=10,                            # Maximum results to return
    output_fields=["id", "text"]
)

Résultats de la recherche :

doc_id

text

1

"L'apprentissage automatique renforce l'efficacité de l'analyse des données à grande échelle"

3

"Les architectures de machines d'apprentissage profond optimisent les charges de calcul.

Exemple : slop = 3

Dans cet exemple, un slop de 3 offre encore plus de flexibilité. Le filtre recherche "machine learning" avec un maximum de trois positions de jetons autorisées entre les mots.

# Example: Filter documents containing "machine learning" with slop=3
filter_slop3 = "PHRASE_MATCH(text, 'machine learning', 3)"

result_slop2 = client.search(
    collection_name="tech_articles",
    anns_field="embeddings",             # Vector field name
    data=[query_vector],                 # Query vector
    filter=filter_slop3,                 # Filter expression
    search_params={"params": {"nprobe": 10}},
    limit=10,                            # Maximum results to return
    output_fields=["id", "text"]
)

Résultats de la recherche :

doc_id

text

1

"L'apprentissage automatique renforce l'efficacité de l'analyse des données à grande échelle.

2

"L'apprentissage d'une approche basée sur la machine est vital pour les progrès de l'IA moderne"

3

"Les architectures de machines d'apprentissage profond optimisent les charges de calcul

5

"L'apprentissage d'algorithmes avancés augmente les capacités de l'IA".

Éléments à prendre en compte

  • L'activation de la recherche de phrases pour un champ déclenche la création d'un index inversé, qui consomme des ressources de stockage. Tenez compte de l'impact sur le stockage lorsque vous décidez d'activer cette fonctionnalité, car il varie en fonction de la taille du texte, des tokens uniques et de l'analyseur utilisé.

  • Une fois que vous avez défini un analyseur dans votre schéma, ses paramètres deviennent permanents pour cette collection. Si vous décidez qu'un autre analyseur répondrait mieux à vos besoins, vous pouvez envisager d'abandonner la collection existante et d'en créer une nouvelle avec la configuration d'analyseur souhaitée.

  • La performance de la correspondance des phrases dépend de la façon dont le texte est symbolisé. Avant d'appliquer un analyseur à l'ensemble de votre collection, utilisez la méthode run_analyzer pour examiner le résultat de la tokenisation. Pour plus d'informations, reportez-vous à la section Vue d'ensemble de l'analyseur.

  • Règles d'échappement dans les expressions filter:

    • Les caractères placés entre guillemets doubles ou simples dans les expressions sont interprétés comme des constantes de chaîne. Si la constante de chaîne comprend des caractères d'échappement, ceux-ci doivent être représentés par une séquence d'échappement. Par exemple, utilisez \\ pour représenter \, \\t pour représenter une tabulation \t, et \\n pour représenter une nouvelle ligne.

    • Si une constante de chaîne est entourée de guillemets simples, un guillemet simple à l'intérieur de la constante doit être représenté par \\', tandis qu'un guillemet double peut être représenté par " ou \\". Exemple : 'It\\'s milvus'.

    • Si une constante de chaîne est entourée de guillemets doubles, un guillemet double à l'intérieur de la constante doit être représenté par \\" tandis qu'un guillemet simple peut être représenté par ' ou \\'. Exemple : "He said \\"Hi\\"".