Milvus python库 pymilvus 常用操作详解之Collection(下)
上篇博客 Milvus python库 pymilvus 常用操作详解之Collection(上) 主要介绍了 pymilvus 库中Collection集合的相关概念以及创建过程的代码实现,现在我们要在该基础上实现对于collection中插入数据的混合检索(基于dense vector 和 sparse vector)。
首先回顾一下我们创建的名为 hybrid_demo
的集合的基本信息:
print(col)
# 可以看到集合的基本信息,该集合包含四个字段,主键id,检索文字内容text,稠密向量 dense_vector 和 稀疏向量 sparse_vector
<Collection>:
-------------
<name>: hybrid_demo
<description>:
<schema>: {'auto_id': True, 'description': '', 'fields': [{'name': 'pk', 'description': '', 'type': <DataType.VARCHAR: 21>, 'params': {'max_length': 100}, 'is_primary': True, 'auto_id': True}, {'name': 'text', 'description': '', 'type': <DataType.VARCHAR: 21>, 'params': {'max_length': 512}}, {'name': 'sparse_vector', 'description': '', 'type': <DataType.SPARSE_FLOAT_VECTOR: 104>}, {'name': 'dense_vector', 'description': '', 'type': <DataType.FLOAT_VECTOR: 101>, 'params': {'dim': 1024}}], 'enable_dynamic_field': False}
因为我们想实现的检索功能是基于两个向量表达的混合检索,所以需要将名为 dense_vector
和 sparse_vector
的字段设置为针对于向量数据的 Index
索引,即 Milvus中有一个重要概念,向量索引。
向量索引
基于 Milvus 提供的官方文档内容,向量索引包含三大类索引,分别是内存索引、磁盘索引和GPU索引。在本篇博客中,我们主要聚焦在内存索引的相关概念和具体实现上。
Milvus 目前只支持一个向量场一种索引类型,当切换索引类型时,旧索引会被自动删除。
ANNS 向量索引
Milvus 支持的大多数向量索引类型都使用近似近邻检索(ANNS)算法。
何为近似近邻检索(ANNS)算法?(ChatGPT-4o回答 & Milvus 内存索引 原文内容)
近似近邻检索(Approximate Nearest Neighbor Search, ANNS)是一种用于快速寻找大规模数据集中近似最近邻的算法。传统的最近邻搜索在高维数据中计算量很大,因此ANNS方法通过引入近似来提高效率,允许在较短时间内找到与查询点距离最接近的点,虽然结果可能不是最优的,但通常足够接近并且计算速度快。
与通常非常耗时的精确检索相比,ANNS 的核心理念不再局限于返回最精确的结果,而是只搜索目标的近邻。ANNS 通过在可接受的范围内牺牲精确度来提高检索效率。
根据实现方法,ANNS 向量索引可分为四种类型:基于树、基于图、基于哈希和基于量化。
ANNS 向量索引类型 | 实际例子 | 描述 |
---|---|---|
基于树 | KD-Tree | 使用树状结构递归划分空间,适用于低维数据集的快速检索。 |
基于图 | HNSW(Hierarchical Navigable Small World) | 构建多层次小世界图,用于大规模高维数据集的高效搜索。 |
基于哈希 | LSH(Locality-Sensitive Hashing) | 通过哈希函数将相似数据点映射到相同桶中,适合高维空间的快速匹配。 |
基于量化 | PQ(Product Quantization) | 将高维向量分解并量化以减少存储和计算成本,适用于大型数据库的图像检索。 |
Milvus 支持的索引
Milvus 支持多种索引类型,这些类型按其处理的向量嵌入类型分为:浮点嵌入(也称浮点向量或密集/稠密向量)、二进制嵌入(也称二进制向量)和稀疏嵌入(也称稀疏向量)。
本篇文章中主要介绍基于稠密向量和稀疏向量的索引类型,二进制向量暂不介绍。
一、稠密向量的索引
既然我们需要通过ANNS近似近邻检索的方式去找到与某个向量表示最相关的若干个向量,那我们就得有度量向量之间距离的计算方式。而用于dense vector稠密向量的距离度量是欧氏距离(L2
)、内积(IP
)和 余弦相似度 (COSINE
)。
字段类型 | 维度范围 | 支持的度量类型 | 默认度量类型 |
---|---|---|---|
FLOAT_VECTOR | 2-32,768 | COSINE, L2, IP | COSINE |
FLOAT16_VECTOR | 2-32,768 | COSINE, L2, IP | COSINE |
BFLOAT16_VECTOR | 2-32,768 | COSINE, L2, IP | COSINE |
Milvus 支持的索引类型包括FLAT
,IVF_FLAT
,IVF_PQ
,IVF_SQ8
,HNSW
和SCANN
,用于基于 CPU 的 ANN 搜索。(若想了解每个索引类型的特点和适用场景,请参考官方文档)
在后续的代码实现中,我们将采用唯一能保证精确搜索结果的索引类型,即FLAT,并搭配内积IP度量类型实现混合检索。
对于要求完美准确性并依赖相对较小(百万量级)数据集的向量相似性搜索应用,FLAT 索引是一个不错的选择。
FLAT 不压缩向量,是唯一能保证精确搜索结果的索引。
FLAT 的结果还可以作为其他召回率低于 100% 的索引所产生结果的比较点。
FLAT 的精确度很高,因为它采用的是穷举搜索方法,这意味着每次查询都要将目标输入与数据集中的每一组向量进行比较,这使得 FLAT 成为列表中速度最慢的索引,而且不适合查询海量向量数据。
在 Milvus 中,FLAT 索引不需要任何参数,使用它也不需要数据训练。
二、稀疏向量的索引
不同于稠密向量支持三种距离度量,稀疏向量支持的距离度量只有IP
。
稀疏向量的索引类型包括SPARSE_INVERTED_INDEX
和SPARSE_WAND
:
支持的索引 | 分类 | 方案 |
---|---|---|
稀疏反转索引 | 倒置索引 | • 取决于相对较小的数据集 • 要求100%的召回率 |
稀疏反向索引 | 反向索引 | • 弱AND算法加速 • 在牺牲少量召回率的同时,速度也有明显提高 |
混合索引代码实现
一、为两个向量字段创建index
sparse_index = {"index_type": "SPARSE_INVERTED_INDEX", "metric_type": "IP"}
# 为名为"sparse_vector"的稀疏向量字段创建SPARSE_INVERTED_INDEX类型,向量度量方式为IP的索引
col.create_index("sparse_vector", sparse_index)
dense_index = {"index_type": "FLAT", "metric_type": "IP"}
# 为名为"dense_vector"的稠密向量字段创建FLAT类型,向量度量方式为IP的索引
col.create_index("dense_vector", dense_index)
# 集合调用load()函数,索引文件和所有字段的原始数据都将加载到内存中,以便快速响应搜索和查询
# 加载集合后插入的实体会自动进行索引并加载
col.load()
二、创建ANNS请求
def get_query_embeddings(query):query_embeddings_raw = model.encode([query], return_dense=True, return_sparse=True, return_colbert_vecs=False)query_embeddings = {}query_embeddings["dense"] = query_embeddings_raw["dense_vecs"]query_embeddings["sparse"] = [dict(query_embeddings_raw["lexical_weights"][0])]return query_embeddingsquery = "请问股票代码为CSCO的美股今日走势如何?"
query_embeddings = get_query_embeddings(query)
# 设置与query向量最相近的向量数量为2,即top 2
k = 2
# 为两个创建了索引的向量字段创建基于ANNS的请求
sparse_search_params = {"metric_type": "IP"}
sparse_req = AnnSearchRequest(query_embeddings["sparse"],"sparse_vector", sparse_search_params, limit=k)
dense_search_params = {"metric_type": "IP"}
dense_req = AnnSearchRequest(query_embeddings["dense"],"dense_vector", dense_search_params, limit=k)
三、进行混合检索
res = col.hybrid_search([sparse_req, dense_req], rerank=RRFRanker(),limit=k, output_fields=['text'])
代码解释(ChatGPT-4o回答):
这行代码是一个混合搜索(hybrid search)操作,结合稀疏和稠密两类请求来进行查询,并使用 RRFRanker 进行重新排序。具体解释如下:
col.hybrid_search
: 对一个集合进行混合搜索。[sparse_req, dense_req]
: 传入两个搜索请求,一个是稀疏(sparse),一个是稠密(dense),即分别基于不同类型的特征进行查询。rerank=RRFRanker()
: 使用 RRFRanker 算法进行结果的重新排序,平衡稀疏和稠密请求的结果。limit=k
: 限定返回的结果数量为k
条。output_fields=['text']
: 返回结果中的text
字段。
RRFRanker(Reciprocal Rank Fusion)是一种排名融合算法,通常用于综合多个排序结果。它通过给每个结果的排名分配一个“倒数权重”,即排名靠前的结果权重大,排名靠后的权重小。RRF的优势在于不依赖于单一排名结果,能够将多个基础排名的优势有效结合起来,从而生成一个更为均衡和多样化的最终排名。
四、查看TOP K混合检索结果
for each_res in res:print(each_res)
# 与query最相近的两条检索结果,res列表中的元素是 pymilvus.client.abstract.Hit 数据类型,有 id, distance, entity等属性
"""
id: 454256988014510347, distance: 0.032786883413791656, entity: {'text': '根据股票编号查询股票信息,包括涨跌额、股票名称、开盘价、收盘价、当前价格、最高最低价、竞买价等信息;支持沪深、香港、美国三个市场的股票数据查询,覆盖全球各地的股票信息。'}
id: 454256988014510348, distance: 0.032258063554763794, entity: {'text': '提供最新的新闻头条信息,包括国内、国际、体育、娱乐、科技等各类资讯,让用户获取及时的新闻报道;支持按照不同的新闻分类进行查询,用户可以选择感兴趣的领域,如体育、科技、娱乐等,获取相关的新闻内容。'}
"""
相关文章:

Milvus python库 pymilvus 常用操作详解之Collection(下)
上篇博客 Milvus python库 pymilvus 常用操作详解之Collection(上) 主要介绍了 pymilvus 库中Collection集合的相关概念以及创建过程的代码实现,现在我们要在该基础上实现对于collection中插入数据的混合检索(基于dense vector 和…...

李飞飞:Agent AI 多模态交互的前沿探索
发布于:2024 年 11 月 27 日 星期三 北京 #RAG #李飞飞 #Agent #多模态 #大模型 Agent AI在多模态交互方面展现出巨大潜力,通过整合各类技术,在游戏、机器人、医疗等领域广泛应用。如游戏中优化NPC行为,机器人领域实现多模态操作等。然而,其面临数据隐私、偏见、可解释性…...

[October 2019]Twice SQL Injection
有一个登录框和一个注册页面,题目也说这个是二次注入,那么就用二次注入的payload就行 1 union select database()# //爆库 1 union select group_concat(table_name) from information_schema.tables where table_schemactftraining# //爆表 1 union …...

Python爬虫——城市数据分析与市场潜能计算(Pandas库)
使用Python进行城市市场潜能分析 简介 本教程将指导您如何使用Python和Pandas库来处理城市数据,包括GDP、面积和城市间距离。我们将计算每个城市的市场潜能,这有助于了解各城市的经济影响力。 步骤 1: 准备环境 确保您的环境中安装了Python和以下库&…...

如何搭建JMeter分布式集群环境来进行性能测试
在性能测试中,当面对海量用户请求的压力测试时,单机模式的JMeter往往力不从心。如何通过分布式集群环境,充分发挥JMeter的性能测试能力?这正是许多测试工程师在面临高并发、海量数据时最关注的问题。那么,如何轻松搭建…...

【Halcon】 derivate_gauss
1、derivate_gauss Halcon中的derivate_gauss算子是一个功能强大的图像处理工具,它通过将图像与高斯函数的导数进行卷积,来计算各种图像特征。这些特征在图像分析、物体识别、图像增强等领域具有广泛的应用。 参数解释 Sigma:高斯函数的标准差,用于控制平滑的程度。Sigma…...

stm32中systick时钟pinlv和系统节拍频率有什么区别,二者有无影响?
在STM32中,SysTick时钟频率和系统节拍频率是两个不同的概念,它们之间存在区别,并且这种区别会对系统的运行产生一定的影响。以下是对这两个概念的详细解释以及它们之间关系的探讨: 一、SysTick时钟频率 定义:SysTick…...

柔性数组详解+代码展示
系列文章目录 🎈 🎈 我的CSDN主页:OTWOL的主页,欢迎!!!👋🏼👋🏼 🎉🎉我的C语言初阶合集:C语言初阶合集,希望能…...

前端入门指南:Webpack插件机制详解及应用实例
前言 在现代前端开发中,模块化和构建工具的使用变得越来越重要,而Webpack作为一款功能强大的模块打包工具,几乎成为了开发者的默认选择。Webpack不仅可以将各种资源(如JavaScript文件、CSS文件、图片等)打包成优化后的…...

C++备忘录模式
在读《大话设计模式》,在此记录有关C实现备忘录模式。 场景引入:游戏中的存档,比如打boss之前记录人物的血量等状态。 下面代码是自己根据理解实现的存档人物血量功能。 #include <iostream>using namespace std;//声明玩家类 class …...

【Electron学习笔记(四)】进程通信(IPC)
进程通信(IPC) 进程通信(IPC)前言正文1、渲染进程→主进程(单向)2、渲染进程⇌主进程(双向)3、主进程→渲染进程 进程通信(IPC) 前言 在Electron框架中&…...

Java 中的 remove 方法深度解析
在 Java 编程中,remove方法是一个经常被使用的操作。它可以用于从各种数据结构中移除特定的元素,帮助我们有效地管理和操作数据。本文将深入探讨 Java 中的remove方法,包括在不同数据结构中的应用、使用场景、注意事项以及性能考虑等方面。 …...

企业品牌曝光的新策略:短视频矩阵系统
企业品牌曝光的新策略:短视频矩阵系统 在当今数字化时代,短视频已经渗透到我们的日常生活之中,成为连接品牌与消费者的关键渠道。然而,随着平台于7月20日全面下线了短视频矩阵的官方接口,许多依赖于此接口的小公司和内…...

【初阶数据结构与算法】二叉树顺序结构---堆的应用之堆排、Top-K问题
文章目录 一、堆排引入之使用堆排序数组二、真正的堆排1.向上调整算法建堆2.向下调整算法建堆3.向上和向下调整算法建堆时间复杂度比较4.建堆后的排序4.堆排序和冒泡排序时间复杂度以及性能比较 三、Top-K问题 一、堆排引入之使用堆排序数组 在了解真正的堆排之前,我…...

vue3 + ts 使用 el-tree
实现效果: 代码: <template><!-- el-tree 使用 --><div class"my-tree-container"><el-scrollbar height"100%"><el-tree ref"treeRef" :data"treeData" node-key"id" n…...

Create Stunning Word Clouds with Ease!
Looking to craft breathtaking word clouds? WordCloudStudio is your go-to solution! Whether you’re a marketer, educator, designer, or simply someone who loves visualizing data, this app has everything you need. Download now: https://apps.apple.com/app/wor…...

html+css网页设计 旅游 马林旅行社5个页面
htmlcss网页设计 旅游 马林旅行社5个页面 网页作品代码简单,可使用任意HTML辑软件(如:Dreamweaver、HBuilder、Vscode 、Sublime 、Webstorm、Text 、Notepad 等任意html编辑软件进行运行及修改编辑等操作)。 获取源码 1&#…...

python selenium(4+)+chromedriver最新版 定位爬取嵌套shadow-root(open)中内容
废话不多说,直接开始 本文以无界作为本文测试案例,抓取shadow-root(open)下的内容 shadow Dom in selenium: 首先先讲一下shadow Dom in selenium 版本的区别,链接指向这里 在Selenium 4版本 以及 chrom…...

React基础教程(11):useCallback记忆函数的使用
11、useCallback记忆函数 防止因为组件重新渲染,导致方法被重新创建,起到缓存作用,只有第二个参数变化了,才重新声明一次。 示例代码: import {useCallback, useState} from "react";const App = () =>...

arp-scan 移植到嵌入式 Linux 系统是一个涉及多个步骤的过程
将 arp-scan 移植到嵌入式 Linux 系统是一个涉及多个步骤的过程。arp-scan 是一个用于发送 ARP 请求以发现网络上设备的工具,它依赖于一些标准的 Linux 库和工具。以下是将 arp-scan 移植到嵌入式 Linux 系统的基本步骤: 1. 获取 arp-scan 源码 首先&a…...

【Linux】常用命令一
声明:以下内容均学习自《Linux就该这么学》一书。 Linux中的shell是一种命令行工具,它充当的作用是人与内核(硬件)之间的翻译官。 大多数Linux系统默认使用的终端是Bash解释器。 1、echo 用于在终端输出字符串或变量提取后的值。 echo "字符串…...

在鲲鹏麒麟服务器上部署MySQL主从集群
因项目需求需要部署主从MySQL集群,继续采用上次的部署的MySQL镜像arm64v8/mysql:latest,版本信息为v8.1.0。计划部署服务器192.168.31.100和192.168.31.101 部署MySQL主节点 在192.168.31.100上先创建好/data/docker/mysql/data和/data/docker/mysql/l…...
Siknhorn算法介绍
SiknHorn算法是一个快速求解离散优化问题的经典算法,特别适用于计算离散分布之间的**最优传输(Optimal Transport)**距离; 最优传输问题介绍 计算两个概率分布 P 和 Q 之间的传输成本,通常表示为: 是传输…...

群控系统服务端开发模式-应用开发-邮箱短信通道功能开发
邮箱短信通道主要是将邮箱及短信做归属的。具体见下图: 一、创建表 1、语句 CREATE TABLE cluster_control.nc_param_emailsms (id int(11) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT 编号,email_id varchar(120) CHARACTER SET utf8 COLLATE utf8_general_ci NO…...

[docker中首次配置git环境]
11月没写东西,12月初赶紧水一篇。 刚开始搭建docker服务器时,网上找一堆指令配置好git后,再次新建容器后忘记怎么配了,,这次记录下。 一、git ssh指令法,该方法不用每次提交时输入密码 前期准备࿰…...

书生浦语·第四期作业合集
目录 1. Linux基础知识 1.1-Linux基础知识 1.在终端通过ssh 端口映射连接开发机 2. 创建helloworld.py 3.安装相关包并运行 4.端口映射并访问相关网页...

5G学习笔记之PRACH
即使是阴天,也要记得出门晒太阳哦 目录 1. 概述 2. PRACH Preamble 3. PRACH Preamble 类型 3.1 长前导码 3.2 短前导码 3.3 前导码格式与小区覆盖 4. PRACH时频资源 4.1 小区所有可用PRACH资源 4.2 SSB和RACH的关系 4.3 PRACH时频资源配置 1. 概述 随机接入…...

Ubuntu24.04配置DINO-Tracker
一、引言 记录 Ubuntu 配置的第一个代码过程 二、更改conda虚拟环境的默认安装路径 鉴于不久前由于磁盘空间不足引发的重装系统的惨痛经历,在新系统装好后当然要先更改虚拟环境的默认安装路径。 输入指令: conda info可能因为我原本就没有把 Anacod…...

抓包之查看websocket内容
写在前面 本文看下websocket抓包相关内容。 1:正文 websocket基础环境搭建参考这篇文章。 启动后,先看chrome的network抓包,这里我们直接使用is:running来过滤出websocket的请求: 可以清晰的看到发送的内容以及响应的内容。在…...

【Leetcode Top 100】21. 合并两个有序链表
问题背景 将两个升序链表合并为一个新的 升序 链表并返回。新链表是通过拼接给定的两个链表的所有节点组成的。 数据约束 两个链表的节点数目范围是 [ 0 , 50 ] [0, 50] [0,50] − 100 ≤ N o d e . v a l ≤ 100 -100 \le Node.val \le 100 −100≤Node.val≤100 l 1 l_1 …...