Alibaba Cloud Elasticsearch V8.0 et les versions ultérieures prennent en charge la recherche des k plus proches voisins (kNN), qui identifie les vecteurs les plus similaires à un vecteur de requête. La recherche kNN permet de mettre en œuvre des cas d'utilisation tels que :
Recherche d'images et empreinte vidéo : Trouvez des images visuellement similaires ou des segments vidéo quasi identiques
Reconnaissance faciale et vocale : Faites correspondre les vecteurs biométriques avec les profils stockés
Recommandation de produits : Récupérez les articles dont les vecteurs de caractéristiques sont les plus proches du vecteur de préférence de l'utilisateur
Fonctionnement
Stockez vos données sous forme de champs dense_vector dans un index Elasticsearch. Lorsque vous exécutez une recherche kNN, Elasticsearch calcule la similarité entre votre vecteur de requête et le vecteur de chaque document, puis renvoie les k correspondances les plus proches.
Deux méthodes de recherche sont disponibles :
| Méthode de recherche | Interface de requête | Stockage en mémoire | Exigence de mappage |
|---|---|---|---|
| Recherche kNN approximative | API Search avec les paramètres knn |
Oui | Définissez index: true sur les champs dense_vector |
| Recherche kNN exacte | Requête script_score avec une fonction vectorielle |
Oui | Définissez index: false ou laissez vide |
Dans la plupart des cas, utilisez la recherche kNN approximative. Elle renvoie des résultats avec une latence plus faible, au prix d'une précision légèrement réduite. La recherche kNN exacte garantit des résultats précis, mais effectue une analyse exhaustive de tous les documents correspondants et ne convient pas aux ensembles de données à grande échelle.
Prérequis
Avant de commencer, assurez-vous de disposer des éléments suivants :
Un cluster Alibaba Cloud Elasticsearch V8.x. Ce guide utilise la version V8.5.1 à titre d'exemple. Pour les instructions de configuration, consultez Créer un cluster Alibaba Cloud Elasticsearch.
Des données métier converties en représentations vectorielles et stockées dans des champs
dense_vector. Concevez vos vecteurs de sorte que les documents plus similaires à une requête possèdent des vecteurs plus proches du vecteur de requête, selon la métrique de similarité choisie.
Remarques d'utilisation
Les champs
dense_vectorne prennent pas en charge l'agrégation ni le tri.Les champs de type
nestedne prennent pas en charge la recherche kNN approximative.Dans les scénarios de recherche inter-clusters, le paramètre
ccs_minimize_roundtripsn'est pas pris en charge avec la recherche kNN.La recherche kNN utilise par défaut le type de recherche
dfs_query_then_fetch. Le paramètresearch_typene peut pas être défini explicitement lors de l'exécution d'une recherche kNN.
Recherche kNN approximative
Considérations relatives aux performances
La recherche kNN approximative utilise des graphes HNSW (Hierarchical Navigable Small World) pour indexer les vecteurs denses par segment. La construction des graphes HNSW lors de l'indexation consomme beaucoup de ressources. Pour maintenir des performances stables :
Augmentez le délai d'expiration du client et utilisez des requêtes d'écriture en bloc lors de l'indexation des données vectorielles.
Réduisez le nombre de segments ou fusionnez tous les segments en un seul afin d'améliorer la vitesse de recherche.
Vérifiez que la mémoire des nœuds de données dépasse la taille combinée de toutes les données vectorielles et des structures d'index HNSW.
Évitez les opérations d'écriture ou de mise à jour volumineuses pendant l'exécution d'une recherche kNN approximative.
Créer un index
Définissez index: true et configurez le paramètre similarity lors de la définition des champs dense_vector.
PUT image-index
{
"mappings": {
"properties": {
"image-vector": {
"type": "dense_vector",
"dims": 3,
"index": true,
"similarity": "l2_norm"
},
"title": {
"type": "text"
},
"file-type": {
"type": "keyword"
}
}
}
}
Paramètres du champ dense_vector
Pour la référence complète des paramètres, consultez dense-vector.
| Paramètre | Description |
|---|---|
type |
Définissez sur dense_vector. |
dims |
Nombre de dimensions par vecteur. Le maximum est de 1024 lorsque index: true, et de 2048 lorsque index: false. |
index |
Définissez sur true pour construire un index HNSW destiné à la recherche kNN approximative. Valeur par défaut : false. |
similarity |
Algorithme de similarité utilisé pour noter les correspondances. Obligatoire lorsque index: true. Consultez le tableau ci-dessous. |
Algorithmes de similarité pris en charge
| Valeur | Algorithme | Formule de score |
|---|---|---|
l2_norm |
Distance euclidienne | 1 / (1 + l2_norm(query, vector)^2) |
dot_product (float) |
Produit scalaire — les deux vecteurs doivent être normalisés à une longueur unitaire | (1 + dot_product(query, vector)) / 2 |
dot_product (byte) |
Produit scalaire — les deux vecteurs doivent avoir la même longueur | 0.5 + (dot_product(query, vector) / (32768 × dims)) |
cosine |
Similarité cosinus | (1 + cosine(query, vector)) / 2 |
L'algorithme cosine ne prend pas en charge les vecteurs ayant une valeur de 0.
La recherche kNN approximative est prise en charge dans Elasticsearch V8.0 et les versions ultérieures. Si votre cluster a été mis à niveau depuis une version antérieure à la V8.0, recréez l'index et définissez index: true sur tous les champs dense_vector avant d'exécuter des recherches kNN approximatives.
Écrire des données
POST image-index/_bulk?refresh=true
{ "index": { "_id": "1" } }
{ "image-vector": [1, 5, -20], "title": "moose family", "file-type": "jpg" }
{ "index": { "_id": "2" } }
{ "image-vector": [42, 8, -15], "title": "alpine lake", "file-type": "png" }
{ "index": { "_id": "3" } }
{ "image-vector": [15, 11, 23], "title": "full moon", "file-type": "jpg" }
Exécuter une recherche kNN approximative
Utilisez le paramètre knn dans l'API Search. L'API de recherche kNN est dépréciée depuis Elasticsearch V8.4 et les versions ultérieures.
POST image-index/_search
{
"knn": {
"field": "image-vector",
"query_vector": [-5, 9, -12],
"k": 10,
"num_candidates": 100
},
"fields": [ "title", "file-type" ]
}
Paramètres de recherche kNN
Pour la référence complète des paramètres, consultez Search API.
| Paramètre | Obligatoire | Description |
|---|---|---|
field |
Oui | Nom du champ dense_vector à rechercher. |
query_vector |
Oui | Vecteur de requête. Il doit comporter le même nombre de dimensions que le champ cible. |
k |
Oui | Nombre de plus proches voisins à renvoyer. Doit être inférieur à num_candidates. |
num_candidates |
Oui | Nombre de candidats de plus proches voisins évalués par shard. Maximum : 10 000. Une valeur plus élevée améliore la précision mais augmente la latence. |
filter |
Non | Filtre DSL de requête appliqué pendant la recherche. Renvoie les k premiers documents correspondant au filtre. S'il est omis, tous les documents sont pris en compte. |
Recherche kNN exacte
Créer un index
Définissez index: false (ou laissez vide) pour éviter la construction d'un index HNSW.
PUT zl-index
{
"mappings": {
"properties": {
"product-vector": {
"type": "dense_vector",
"dims": 5,
"index": false
},
"price": {
"type": "long"
}
}
}
}
| Paramètre | Description |
|---|---|
type |
Définissez sur dense_vector. |
dims |
Nombre de dimensions par vecteur. |
index |
Valeur par défaut : false. Définissez sur false ou laissez vide pour améliorer l'efficacité de la recherche kNN exacte. |
Écrire des données
POST zl-index/_bulk?refresh=true
{ "index": { "_id": "1" } }
{ "product-vector": [230.0, 300.33, -34.8988, 15.555, -200.0], "price": 1599 }
{ "index": { "_id": "2" } }
{ "product-vector": [-0.5, 100.0, -13.0, 14.8, -156.0], "price": 799 }
{ "index": { "_id": "3" } }
{ "product-vector": [0.5, 111.3, -13.0, 14.8, -156.0], "price": 1099 }
Exécuter une recherche kNN exacte
Utilisez la requête script_score avec une fonction vectorielle. L'exemple ci-dessous utilise cosineSimilarity et applique un filtre pour limiter les documents évalués par la fonction vectorielle ; réduire le nombre de documents analysés améliore les performances.
POST zl-index/_search
{
"query": {
"script_score": {
"query": {
"bool": {
"filter": {
"range": {
"price": {
"gte": 1000
}
}
}
}
},
"script": {
"source": "cosineSimilarity(params.queryVector, 'product-vector') + 1.0",
"params": {
"queryVector": [-0.5, 90.0, -10, 14.8, -156.0]
}
}
}
}
}
Fonctions vectorielles prises en charge
Pour la référence complète des fonctions, consultez Functions for vector fields.
| Fonction | Description |
|---|---|
| cosineSimilarity | Similarité cosinus entre le vecteur de requête et le vecteur du document |
| dotProduct | Produit scalaire entre le vecteur de requête et le vecteur du document |
| l1norm | Distance L1 (distance de Manhattan) entre le vecteur de requête et le vecteur du document |
| l2norm | Distance L2 (distance euclidienne) entre le vecteur de requête et le vecteur du document |
Étapes suivantes
k-nearest neighbor (kNN) search — Documentation de référence Elasticsearch