Scoring de pertinence dans la recherche hybride en utilisant la fusion de classement réciproque (RRF, Reciprocal Rank Fusion)
La fusion de classement réciproque (RRF) est un algorithme qui évalue les scores de recherche de plusieurs résultats classés précédemment pour produire un jeu de résultats unifié. Dans Recherche Azure AI, RRF est utilisé chaque fois qu’il existe deux requêtes ou plus qui s’exécutent en parallèle. Chaque requête produit un jeu de résultats classé, et RRF est utilisé pour fusionner et homogénéiser les classements en un seul jeu de résultats, retourné dans la réponse de la requête. Les exemples de scénarios où RRF est toujours utilisé incluent la recherche hybride et plusieurs requêtes vectorielles s’exécutant simultanément.
RRF est basé sur le concept de classement réciproque, qui est l’inverse du rang du premier document pertinent dans une liste de résultats de recherche. L’objectif de la technique est de prendre en compte la position des éléments dans les classements originaux et de donner une importance plus élevée aux éléments classés plus hauts dans plusieurs listes. Cela peut aider à améliorer la qualité et la fiabilité globale du classement final, ce qui le rend plus utile pour la tâche de fusionner plusieurs résultats de recherche triés.
Remarque
Une nouveauté dans 2024-09-01-preview est la possibilité de déconstruire un score de recherche classé par RRF dans ses sous-scores de composant. Cela vous offre une transparence sur la composition de tous les scores. Pour découvrir plus d’informations, voir décompresser des scores de recherche (préversion) dans cet article.
Fonctionnement du classement RRF
RRF fonctionne en prenant les résultats de recherche à partir de plusieurs méthodes, en attribuant un score de classement réciproque à chaque document dans les résultats, puis en combinant les scores pour créer un classement. Le concept est que les documents apparaissant dans les positions supérieures dans plusieurs méthodes de recherche sont susceptibles d’être plus pertinents et doivent être classés plus hauts dans le résultat combiné.
Voici une explication simple du processus RRF :
Obtenez les résultats de recherche classés à partir de plusieurs requêtes s’exécutant en parallèle.
Attribuez des scores de classement réciproques pour les résultats dans chacune des listes classées. RRF génère une nouvelle
@search.score
pour chaque correspondance dans chaque jeu de résultats. Pour chaque document dans les résultats de recherche, le moteur attribue un score de classement réciproque en fonction de sa position dans la liste. Le score est calculé en tant que1/(rank + k)
, oùrank
est la position du document dans la liste etk
est une constante, dont on a observé expérimentalement qu’elle donnait de meilleurs résultats si elle était fixée à une petite valeur comme 60. Notez que cette valeurk
est une constante dans l’algorithme RRF et entièrement distincte duk
qui contrôle le nombre de voisins les plus proches.Combinez les scores. Pour chaque document, le moteur additionne les scores de classement réciproques obtenus à partir de chaque système de recherche, produisant un score combiné pour chaque document.
Le moteur classe les documents en fonction des scores combinés et les trie. La liste résultante est le classement fusionné.
Seuls les champs marqués comme searchable
dans l’index ou searchFields
dans la requête sont utilisés pour le scoring. Seuls les champs marqués comme retrievable
, ou les champs spécifiés dans select
dans la requête, sont retournés dans les résultats de recherche, ainsi que leur score de recherche.
Exécution de requêtes parallèles
RRF est utilisé chaque fois qu’il existe plusieurs exécutions de requête. Les exemples suivants illustrent les modèles de requête où l’exécution de requête parallèle se produit :
- Une requête de texte intégral, ainsi qu’une requête vectorielle (scénario hybride simple), est égale à deux exécutions de requête.
- Une requête de texte intégral, ainsi qu’une requête vectorielle ciblant deux champs vectoriels, est égale à trois exécutions de requête.
- Une requête de texte intégral, ainsi que deux requêtes vectorielles ciblant cinq champs vectoriels, est égale à 11 exécutions de requête
Scores dans les résultats de recherche hybride
Chaque fois que les résultats sont classés, la propriété @search.score
contient la valeur utilisée pour classer les résultats. Les scores sont générés par des algorithmes de classement qui varient pour chaque méthode. Chaque algorithme a sa propre portée et son ampleur.
Le graphique suivant identifie la propriété de scoring retournée sur chaque correspondance, algorithme et plage de scores pour chaque algorithme de classement de pertinence.
Méthode de recherche | Paramètre | Algorithme de scoring | Plage |
---|---|---|---|
recherche en texte intégral | @search.score |
Algorithme BM25 | Pas de limite supérieure. |
recherche vectorielle | @search.score |
Algorithme HNSW, à l’aide de la métrique de similarité spécifiée dans la configuration HNSW. | 0.333 - 1.00 (Cosinus), 0 à 1 pour Euclidean et DotProduct. |
recherche hybride | @search.score |
Algorithme RRF | La limite supérieure est limitée par le nombre de requêtes fusionnées, chaque requête contribuant à un maximum d’environ 1 au score RRF. Par exemple, la fusion de trois requêtes produira des scores RRF plus élevés que la fusion de deux résultats de recherche seulement. |
classement sémantique | @search.rerankerScore |
Classement sémantique | 0.00 - 4.00 |
Le classement sémantique se produit après la fusion RRF des résultats. Son score (@search.rerankerScore
) est toujours signalé séparément dans la réponse de requête. Le classeur sémantique peut reclasser les résultats de la recherche en texte intégral et de la recherche hybride, en supposant que ces résultats incluent des champs ayant du contenu riche sémantiquement. Il peut reclasser des requêtes vectorielles pures si les documents de recherche incluent des champs de texte dont le contenu est sémantiquement pertinent.
Décompresser un score de recherche dans des sous-scores (préversion)
L’utilisation de 2024-09-01-preview vous permet de déconstruire un score de recherche pour afficher ses sous-scores.
Pour les requêtes vectorielles, ces informations peuvent vous aider à déterminer une valeur appropriée pour la pondération de vecteurs ou les seuils minimaux de paramètre.
Pour obtenir des sous-scores :
Utilisez la dernière API REST Recherche dans des documents en préversion ou un package bêta de Kit de développement logiciel (SDK) Azure qui fournit la fonctionnalité.
Modifiez une demande de requête en ajoutant un nouveau paramètre
debug
défini survector
ousemantic
si vous utilisez un classeur sémantique, ouall
.
Voici un exemple de requête hybride qui renvoie des sous-scores en mode débogage :
POST https://{{search-service-name}}.search.windows.net/indexes/{{index-name}}/docs/search?api-version=2024-09-01=preview
{
"vectorQueries": [
{
"vector": [
-0.009154141,
0.018708462,
. . .
-0.02178128,
-0.00086512347
],
"fields": "DescriptionVector",
"kind": "vector",
"exhaustive": true,
"k": 10
},
{
"vector": [
-0.009154141,
0.018708462,
. . .
-0.02178128,
-0.00086512347
],
"fields": "DescriptionVector",
"kind": "vector",
"exhaustive": true,
"k": 10
}
],
"search": "historic hotel walk to restaurants and shopping",
"select": "HotelName, Description, Address/City",
"debug": "vector",
"top": 10
}
Scores pondérés
À l’aide de versions d’API en préversion 2024-07-01 et ultérieures, vous pouvez pondérer les requêtes vectorielles pour augmenter ou diminuer leur importance dans une requête hybride.
Rappelez-vous que lorsque vous calculez le RRF pour un certain document, le moteur de recherche examine le rang de ce document pour chaque jeu de résultats où il apparaît. Supposons qu’un document apparaît dans trois résultats de recherche distincts, où les résultats proviennent de deux requêtes vectorielles et d’une requête de classement BM25 textuelle. La position du document varie dans chaque résultat.
Correspondance trouvée | Position dans les résultats | @search.score | multiplicateur de pondération | @search.score (pondéré) |
---|---|---|---|---|
résultats vectoriels un | Position 1 | 0,8383955 | 0.5 | 0,41919775 |
résultats vectoriels deux | Position 5 | 0,81514114 | 2.0 | 1,63028228 |
Résultats BM25 | Position 10 | 0,8577363 | NA | 0,8577363 |
La position du document dans chaque jeu de résultats correspond à un score initial. Ce score est ajouté pour créer le score RRF final pour ce document.
Si vous ajoutez une pondération vectorielle, les scores initiaux sont soumis à un multiplicateur de pondération qui augmente ou diminue le score. La valeur par défaut est 1,0, ce qui signifie qu’aucune pondération n’est appliquée et que le score initial est utilisé tel quel dans le scoring RRF. Toutefois, si vous ajoutez une pondération de 0,5, le score est réduit et ce résultat devient moins important dans le classement combiné. À l’inverse, si vous ajoutez un poids de 2,0, le score devient un facteur plus important dans le score RRF global.
Dans cet exemple, les valeurs @search.score (pondérées) sont passées au modèle de classement RRF.
Nombre de résultats classés dans une réponse de requête hybride
Par défaut, si vous n’utilisez pas la pagination, le moteur de recherche retourne les 50 correspondances de classement les plus élevées pour la recherche en texte intégral et les correspondances k
les plus similaires pour la recherche vectorielle. Dans une requête hybride, top
détermine le nombre de résultats dans la réponse. En fonction des valeurs par défaut, les 50 correspondances classées les plus élevées du jeu de résultats unifié sont retournées.
Souvent, le moteur de recherche trouve plus de résultats que top
et k
. Pour retourner d’autres résultats, utilisez les paramètres de pagination top
, skip
et next
. La pagination est la façon dont vous déterminez le nombre de résultats sur chaque page logique et parcourez la charge utile complète. Vous pouvez définir maxTextRecallSize
sur des valeurs plus grandes (la valeur par défaut est de 1 000) pour renvoyer davantage de résultats du côté textuel de la requête hybride.
Par défaut, la recherche en texte intégral est soumise à une limite maximale de 1000 correspondances (voir limites de réponse de l’API). Une fois que 1 000 correspondances sont trouvées, le moteur de recherche ne recherche plus d’informations.
Pour plus d’informations, consultez Comment travailler avec des résultats de la recherche.
Diagramme d’un flux de travail de scoring de recherche
Le diagramme suivant illustre une requête hybride qui appelle la recherche vectorielle ou de mots clés, avec un renforcement via des profils de score et un classement sémantique.
Une requête qui génère le flux de travail précédent peut ressembler à ceci :
POST https://{{search-service-name}}.search.windows.net/indexes/{{index-name}}/docs/search?api-version=2024-07-01
Content-Type: application/json
api-key: {{admin-api-key}}
{
"queryType":"semantic",
"search":"hello world",
"searchFields":"field_a, field_b",
"vectorQueries": [
{
"kind":"vector",
"vector": [1.0, 2.0, 3.0],
"fields": "field_c, field_d"
},
{
"kind":"vector",
"vector": [4.0, 5.0, 6.0],
"fields": "field_d, field_e"
}
],
"scoringProfile":"my_scoring_profile"
}