当前位置: 首页 > article >正文

使用 KNN 搜索和 CLIP 嵌入构建多模态图像检索系统

作者:来自 Elastic James Gallagher

了解如何使用 Roboflow Inference 和 Elasticsearch 构建强大的语义图像搜索引擎。

在本指南中,我们将介绍如何使用 Elasticsearch 中的 KNN 聚类和使用计算机视觉推理服务器 Roboflow Inference 计算的 CLIP 嵌入构建图像检索系统。

Roboflow Universe 是网络上最大的计算机视觉数据存储库,托管超过 1 亿张图像,它使用 CLIP 嵌入为我们的数据集搜索引擎提供高效的语义查询。

不用多说,让我们开始吧!

CLIP 和 Roboflow 推理简介

CLIP(Contrastive Language-Image Pretraining - 对比语言-图像预训练)是 OpenAI 开发的一种计算机视觉模型架构和模型。该模型于 2021 年根据 MIT 许可发布。

该模型的训练目的是 “根据图像预测最相关的文本片段”。在此过程中,CLIP 学会了通过模型使用的向量来识别图像和文本之间的相似性。 CLIP 将图像和文本映射到向量空间。这允许向量比较并找到与文本查询相似的图像,或与另一幅图像相似的图像。

CLIP 等多模式模型的进步使得构建语义图像搜索引擎变得比以往任何时候都更容易。

像 CLIP 这样的模型可用于创建捕获有关图像或文本查询的语义信息的 “嵌入”。向量嵌入是一种数据表示类型,它将单词、句子和其他数据转换为捕捉其含义和关系的数字。

Roboflow Inference 是一款高性能计算机视觉推理服务器。 Roboflow Inference 支持各种最先进的视觉模型,从用于物体检测的 YOLO11 到用于视觉问答的 PaliGemma 再到用于多模态嵌入的 CLIP。

你可以将 Roboflow Inference 与 Python SDK 一起使用,或者在 Docker 环境中使用。

在本指南中,我们将使用 Inference 计算 CLIP 嵌入,然后将它们存储在 Elasticsearch 集群中,以用于构建图像检索系统。

先决条件

要遵循本指南,你需要:

  • 支持 KNN 搜索的 Elasticsearch 实例
  • 免费的 Roboflow 帐户
  • Python 3.12+

我们准备了一个 Jupyter Notebook,你可以在计算机上或 Google Colab 上运行它,以便按照本指南使用。打开笔记本。

步骤#1:设置支持 KNN 的 Elasticsearch 索引

对于本指南,我们将使用 Elasticsearch Python SDK。你可以使用以下代码来安装它:

pip install elasticsearch

如果你尚未设置 Elasticsearch 集群,请参阅 Elasticsearch 文档以开始使用。

注:你也可以阅读文章 “使用 start-local 脚本在本地运行 Elasticsearch” 开始使用。

安装 SDK 并设置集群后,创建一个新的 Python 文件并添加以下代码以连接到客户端:

from elasticsearch import Elasticsearch

client = Elasticsearch(
	"https://localhost:9200",
	 api_key=“your-api-key",
)

要在 Elasticsearch 中运行嵌入搜索,我们需要一个包含 density_vector 属性类型的索引映射。对于本指南,我们将创建一个包含两个字段的索引:一个包含与图像相关的 CLIP 嵌入的密集向量,以及一个与图像相关的文件名。

运行以下代码来创建索引:

client.indices.create(
	index="knn",
	body={
    	"mappings": {
        	"properties": {
            	"vector": {
                	  "type": "dense_vector",
                	  "dims": 512,
                   "similarity": "cosine",
            	},
            	"filename": {
                	  "type": "keyword",
            	},
        	},
    	},
	}
)

输出应类似于以下内容:

ObjectApiResponse({'acknowledged': True, 'shards_acknowledged': True, 'index': 'knn'})

KNN 搜索使用的默认索引类型是 L2 Norm,也称为欧几里得距离。此距离度量不适用于 CLIP 相似度。因此,上面我们明确表示我们想要创建余弦相似度索引。CLIP 嵌入与余弦相似度相比效果最好。

对于本指南,我们将使用具有 512 个维度的 CLIP 模型。如果你使用其他 CLIP 模型,请确保将 dims 值设置为 CLIP 模型返回的向量的维数。

步骤 2:安装 Roboflow Inference

接下来,我们需要安装 Roboflow Inference 和 Supervision,这是一个用于处理视觉模型预测的工具。你可以使用以下命令安装所需的依赖项:

pip install "inference[clip]" supervision

这将安装 Roboflow Inference 和我们将用于计算向量的 CLIP 模型扩展。

安装 Roboflow Inference 后,我们可以开始计算和存储 CLIP 嵌入。

步骤 3:计算和存储 CLIP 嵌入

在本指南中,我们将为 COCO 128 数据集构建一个语义搜索引擎。此数据集包含从更大的 Microsoft COCO 数据集中采样的 128 张图像。COCO 128 中的图像多种多样,使其成为用于测试我们的语义搜索引擎的理想数据集。

要下载 COCO 128,首先创建一个免费的 Roboflow 帐户。然后,导航到 Roboflow Universe(Roboflow 的开放计算机视觉数据集社区)上的 COCO 128 数据集页面。

单击 “Download Dataset”:

选择 “YOLOv8” 格式。选择显示下载代码的选项:

复制终端命令以下载数据集。该命令应如下所示:

curl -L "https://universe.roboflow.com…r" > roboflow.zip; unzip roboflow.zip; rm roboflow.zip

运行该命令时,数据集将下载到你的计算机并解压。

我们现在可以开始计算 CLIP 嵌入。

从之前的 Python 文件中添加以下代码,然后运行完整文件:

from inference.models import Clip
import os

IMAGE_DIRECTORY = "./COCO-128-2/train/images"

# See a full list of supported models at
# https://inference.roboflow.com/foundation/clip/#how-can-i-use-clip-model-in-inference
clip = Clip(model_id="clip/ViT-B-16")

# create index if it doesn't exist for KNN with two fields: vector and file name
for file in os.listdir(IMAGE_DIRECTORY):
	if not file.endswith(".jpg"):
    	continue
 	 
	image_path = os.path.join(IMAGE_DIRECTORY, file)
	vector = clip.embed_image(image_path)

	client.index(
    	index="demo",
    	body={
        	"vector": vector.tolist()[0],
        	"filename": file,
    	}
	)

这段代码会遍历 COCO 128 数据集训练集中的所有图像,并通过 Roboflow Inference 使用 CLIP 模型对它们进行处理。然后,我们将生成的向量与每个向量关联的文件名一起索引到 Elasticsearch 中。

CLIP 模型权重可能需要 1-2 分钟才能下载。完成此操作时,你的脚本将暂时暂停。然后,CLIP 模型权重将缓存在你的系统中以供将来使用。

注意:运行上述代码时,你可能会看到一些与 ExecutionProviders 相关的警告。这与 Inference 中针对不同设备的可用优化有关。例如,如果你在 CUDA 上部署,CoreMLExecutionProvide 将不可用,因此会发出警告。看到这些警告时无需采取任何措施。

步骤 4:从 Elasticsearch 检索数据

索引数据后,即可运行测试查询!

要使用文本作为输入,你可以使用此代码检索用于运行搜索的输入向量:

query_vector = clip.embed_text("coffee")

要使用图像作为输入,你可以使用以下代码:

query_vector = clip.embed_image(“path/to/image”)

在本指南中,我们使用查询“coffee”运行文本搜索。

我们将使用 k-最近邻 (k-nearest neighbours - KNN) 搜索。此搜索类型接受输入嵌入并在我们的数据库中查找嵌入与输入相似的值。KNN 搜索通常用于向量比较。

KNN 搜索始终返回前 k 个最近邻。如果 k = 3,Elasticsearch 将返回与输入向量最相似的三个文档。

使用 Elasticsearch, 你可以在几毫秒内从大型向量存储中检索结果。

我们可以使用以下代码运行 KNN 搜索:

import supervision as sv
from PIL import Image

response = client.search(
	index="demo",
	body={
    	"query": {
        	"knn": {
            	"field": "vector",
            	"query_vector": query_vector.tolist()[0],  # The input vector
            	"k": 3
        	}
    	}
	}
)

images = [Image.open(os.path.join(IMAGE_DIRECTORY, i["_source"]["filename"])) for i in response["hits"]["hits"][:3]]

sv.plot_images_grid(images, grid_size=(1, 3))

上面的 k 值表示应从每个分片中检索多少个最近的向量。查询的大小参数决定要返回多少个结果。由于我们在此演示中使用一个分片,因此查询将返回三个结果。

我们的代码返回:

我们已成功运行语义搜索并找到与输入查询相似的图像!上面,我们可以看到三张最相似的图像:一张户外桌子上的咖啡杯和蛋糕的照片,然后是我们索引中的两张桌子上有咖啡杯的重复图像。

结论

借助 Elasticsearch 和 Roboflow Inference 中的 CLIP 功能,你可以创建一个多模态搜索引擎。你可以使用搜索引擎进行图像检索、图像比较和重复数据删除、带有视觉提示的多模态检索增强生成等。

Roboflow 大规模使用 Elasticsearch 和 CLIP。我们存储了超过 1 亿个 CLIP 嵌入并对其进行索引,以供希望大规模搜索数据集的客户进行多模态搜索。随着我们平台上的数据从数百张图像增长到数亿张,Elasticsearch 实现了无缝扩展。

要了解有关使用 Roboflow Inference 的更多信息,请参阅 Roboflow Inference 文档。要为你的下一个计算机视觉项目查找数据,请查看 Roboflow Universe。

想要获得 Elastic 认证?了解下一次 Elasticsearch 工程师培训何时开始!

Elasticsearch 包含许多新功能,可帮助你为你的用例构建最佳搜索解决方案。深入了解我们的示例笔记本以了解更多信息,开始免费云试用,或立即在本地机器上试用 Elastic。

原文:Build a multimodal image retrieval system using KNN search and CLIP embeddings - Elasticsearch Labs


http://www.kler.cn/a/523685.html

相关文章:

  • Linux文件原生操作
  • 【C语言练习题】整数和实数在计算机中的二进制表示
  • sudo nvim /path/yourfile, sudo: nvim: command not found
  • 内网穿透实现MC联机
  • git困扰的问题
  • 实践网络安全:常见威胁与应对策略详解
  • [论文总结] 深度学习在农业领域应用论文笔记14
  • 人工智能:农业领域的变革力量
  • 如何制作浪漫风格的壁纸
  • 【PowerShell专栏】利用PowerShell开启端口的监听
  • GEE | 提取随机样本点的数据,以CHIRPS降水为例
  • Kotlin函数式API
  • 【蓝桥杯嵌入式入门与进阶】2.与开发板之间破冰:初始开发板和原理图2
  • 【Java基础-41.5】深入解析Java异常链:构建清晰的错误追踪体系
  • [Dialog屏幕开发] 设置搜索帮助
  • 双指针算法精解:对撞指针与快慢指针的妙用与实践
  • 2025年大数据毕业设计选题推荐:数据分析与可视化 数据挖掘
  • 获取metadata耗时对比(libtag/ffmpeg/gstreamer)
  • 第 5 章:声音与音乐系统
  • 一文大白话讲清楚webpack基本使用——17——Tree Shaking
  • [Dialog屏幕开发] 屏幕绘制(使用向导创建Tabstrip Control标签条控件)
  • Java 9模块开发:IntelliJ IDEA实战指南
  • Transformation,Animation and Viewing
  • 高通Yocto项目 - 全解析
  • 【MQ】探索 Kafka
  • 【Unity3D】Unity混淆工具Obfuscator使用