Jean's Blog

一个专注软件测试开发技术的个人博客

0%

RAG组件--向量数据库检索(搜索)、度量类型和条件过滤

度量类型

距离度量的标准(类型)

image-20250822101843966

L2(欧氏距离)

  • 适用于连续数值型特征,如图像像素或声纹特征;
  • 常见于需要精确度量“几何距离”的场景,例如视觉检索、点云匹配等。

  • 适用场景: 连续数值型特征(如图像像素、声纹特征),需要精确度量几何距离的场景(视觉检索、点云匹配)

  • 特性: 值越小相似度越高,范围$[0,∞)$
  • 公式:$L2= \sqrt{\sum(A-B)^2}$

IP(内积)

  • 在向量长度(范数)有意义时使用,比如评估未归一化嵌入向量的匹配强度;
  • 若向量已归一化,等价于余弦相似度,可用于文本或推荐系统中的评分计算。

  • 适用场景: 向量长度(范数)有意义时(如未归一化的嵌入向量)

  • 特性: 值越大相似度越高,范围无限制
  • 公式: $IP = A \cdot B = \sum(A_1B_1 + A_2B_2 + …)$
  • 注意: 若向量已归一化,等价于余弦相似度

COSINE(余弦相似度)

  • 最常用于文本、自然语言嵌入之间的语义相似性计算;
  • 不受向量长度影响,关注方向一致性,适合主题或意图匹配。

  • 适用场景: 文本/NLP嵌入的语义相似性计算,主题或意图匹配

  • 特性: 值越大相似度越高,范围$[-1,1]$
  • 公式:$cos(θ)=\frac{A \cdot B}{|A||B|}$
  • 黄金标准: 文本检索不知道选什么时首选余弦

JACCARD(交并比距离)

  • 用于集合或二值特征的相似度评估,如标签集合、关键词重叠;
  • 在文本片段重叠、推荐系统中基于兴趣标签的匹配场景常见。
  • 适用场景: 集合或二值特征的相似度评估(标签集合、关键词重叠)
  • 特性: 值越小相似度越高,范围$[0,1]$
  • 公式:$J=1-\frac{|A∩B|}{|A∪B|}$

HAMMING(海明距离)

  • 专用于二进制向量(如感知哈希、二值化特征)的相似度度量;
  • 常见于图像指纹检索、人脸二值编码或者简易哈希匹配场景。

  • 适用场景: 二进制向量(感知哈希、二值化特征)

  • 特性: 值越小相似度越高,范围$[0,dim]$

BM25(全文检索评分)

  • 专为稀疏向量上的全文搜索设计,结合 TF、IDF 和文档长度归一化;
  • 适用于文档检索、问答系统的倒排索引搜索场景。

  • 适用场景: 稀疏向量上的全文搜索(文档检索、问答系统)

  • 特性: 值越大相似度越高,范围$[0,∞)$

各种字段所支持的度量类型

字段类型 维度范围 支持的度量类型 默认度量类型
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
SPARSE_FLOAT_VECTOR 无需指定 IP、BM25(仅限全文检索) IP
BINARY_VECTOR 8 – (32 768x8) HAMMING、JACCARD HAMMING
  • FLOAT/FLOAT16/BFLOAT16 VECTOR:
    • 维度范围: 2-32768
    • 支持: COSINE, L2, IP
    • 默认: COSINE
  • SPARSE FLOAT VECTOR:
    • 无需指定维度
    • 支持: IP、BM25(仅限全文检索)
    • 默认: IP
  • BINARY VECTOR:
    • 维度范围: 8-(32768×8)
    • 支持: HAMMING, JACCARD
    • 默认: HAMMING

各种度量类型的取值范围

度量类型 相似度/距离特性 数值范围
L2 (欧氏距离) 值越小,相似度越高 [0,∞)
IP (内积) 值越大,相似度越高 [−1,1]
COSINE (余弦) 值越大,相似度越高 [−1,1]
JACCARD 值越小,相似度越高 [0,1]
HAMMING 值越小,相似度越高 [0,dim)
BM25 值越大,相似度越高 [0,∞)

关键注意: 不同度量类型的数值范围差异很大,如欧式距离可能大于1是正常的

ANN搜索

Milvus的ANN搜索是一种高效的向量相似度搜索方法,它通过预构建的索引文件来加速搜索过程。与kNN搜索相比,ANN搜索不需要遍历所有向量,而是通过索引快速定位可能包含最相似向量的子集,从而大大提高了搜索效率。

image-20250822101723764

  • 核心原理: 通过预构建的索引文件加速搜索过程,不需要遍历所有向量,而是快速定位可能包含最相似向量的子集
  • 与kNN区别: ANN(Approximate Nearest Neighbor)是近似搜索,效率高但结果不一定完美;kNN需要精确遍历所有数据
  • 主要特点:
    • 支持单向量和批量向量搜索
    • 可在特定分区内进行搜索
    • 支持多种相似度度量方式(L2、IP、COSINE等)
    • 可通过过滤条件、范围搜索增强效果
    • 支持分页查询和输出字段控制

过滤搜索

image-20250822102907414

标准过滤

  • 原理: 先执行过滤条件筛选数据,再在过滤后的数据集上进行搜索
  • 适用场景: 过滤条件简单且能显著减少数据量的情况

迭代过滤

  • 原理: 边搜索边过滤,动态判断是否满足条件
  • 优势: 处理复杂过滤条件时可能更高效
  • 实现: 通过设置”hints”: “iterative filter”参数启用

范围搜索

范围搜索是在 ANN 搜索结果的基础上,进一步按相似度(或距离)阈值进行筛选,将符合条件的向量返回。

通过两个参数 radius(外圈半径)和 range_filter(内圈半径)构成一对同心圆,返回落在这两个圆之间(或内外圈定义区间内)的所有向量

image-20250822103507782

  • 原理: 在ANN结果基础上,按相似度阈值进一步筛选
  • 参数:
    • radius: 外圈半径
    • range_filter: 内圈半径
  • 效果: 返回落在两个半径定义的环形区域内的向量

分组搜索

目的:在基于向量的相似度搜索结果中,按某个标量字段(如 docId、category)分组,以提高结果多样性,避免同一组内多个相似片段抢占 Top-K。

场景举例:对拆分成多个段落的文档做检索,希望最终返回最相关的文档列表,而不是返回同一文档中多个相似段落。

image-20250822103728847

流程

  1. ANN 检索 对整个集合执行近似最近邻搜索,得到若干最相似实体(chunk)。
  2. 按字段分组 将检索结果按 group_by_field 指定的字段值(如 docId)分桶。
  3. 选取每组 TopN 默认从每个组中取最相似的 1条; 如需更多,可通过 group_size(每组返回条数)和 strict_group_size(是否严格保证每组条数)进行控制。
  4. 整体汇总 最终按组级 TopK(limit)选出若干组,并返回各组内按相似度排序的实体。

混合搜索

同时对同一实体中的多种向量字段(如稠密向量 dense 与稀疏向量 sparse)分别执行 ANN 搜索,将各自返回的 Top-K 结果按得分或排名策略重新融合(rerank),最后输出一个统一的结果集。

目的:融合多模态或多视角特征,提高检索的准确性和鲁棒性。

image-20250822103942383

实现步骤:

  • Embedding 生成
    • 稠密向量(dense):用 BERT、CLIP、其他深度模型生成。
    • 稀疏向量(sparse):用 BM25、SPLADE、BGE-M3 等算法或 Milvus Function 生成。
  • 创建集合并定义多向量字段
    • 在建表时同时包括 FLOAT_VECTOR(稠密)
    • 和 SPARSE_FLOAT_VECTOR(稀疏)字段
    • 并分别建立索引
  • 插入数据
    • 同一条记录同时插入两种向量。
    • 发起多次基础 ANN 搜索
    • 针对每个向量字段构造一个AnnSearchRequest
  • 选择重排序(Reranking)策略
    • WeightedRanker:可为每个向量字段分配权重,强化某些字段的重要性
    • RRFRanker(Reciprocal Rank Fusion):平衡融合,默认参数 k 可调
  • 执行 Hybrid Search
    • limit 决定最终输出的 Top-K 条融合结果。

BM25 全文关键字检索

通过 BM25 对原始文本进行关键词匹配排序,弥补语义向量检索可能忽略精确词条匹配的不足。

image-20250822104341926

优势:

  • 接受原始文本输入,无需手动生成向量;
  • 自动将文本分词、映射为稀疏向量(SPARSE_FLOAT_VECTOR);
  • 适合需精确命中关键术语的场景,如法律、医药、配置文档等;
  • 与稠密向量检索结合,可在 RAG 中实现“语义 + 关键词”双保险。

应用: 可与稠密向量检索结合实现”语义+关键词”双保险

Text Match: 精确文本匹配

精确匹配:基于倒排索引查找包含指定词条的文档,不计算相关度分数,仅返回命中实体。
底层引擎:集成 Tantivy ,针对每个 VARCHAR 字段建立倒排索引,按词条快速定位。

  • 原理: 基于倒排索引查找包含指定词条的文档

  • 特点:

    • 不计算相关度分数,仅返回命中实体
    • 底层集成Tantivy引擎
  • 查询语法:

    • 包含 machine 或 deep: TEXT_MATCH(text, ‘machine deep’)

    • 包含 machine 且包含 deep: TEXT_MATCH(text, ‘machine’) AND TEXT_MATCH(text, ‘deep’)

    • 包含 machine、learning,但不包含 deep:

      TEXT_MATCH(text, ‘machine’)
      AND TEXT_MATCH(text, ‘learning’)
      AND NOT TEXT_MATCH(text, ‘deep’)

搜索和查询

  • 本质区别:
    • 搜索:基于向量相似度,通过距离度量找到相近向量(如余弦相似度)
    • 查询:基于元数据(标量数据)直接定位实体,与向量无关
  • 典型场景:
    • 搜索适用于”找到相似内容”(如推荐系统)
    • 查询适用于”精确查找记录”(如数据库检索)
方法 作用 输入 输出 场景
Get 根据主键查询指定实体 collection_name, ids 指定主键对应的所有字段实体 已知 ID 时最快速地获取完整记录
Query 根据自定义过滤表达式查询指定数量的实体 collection_name, filter, limit 满足条件最多 limit 个实体 需要一次性拿到部分满足条件的结果
QueryIterator 根据自定义过滤表达式按批次 (分页) 遍历所有实体 collection_name, expr, batch_size 通过 iterator.next() 分批返回实体 需要遍历所有满足条件的实体 (流式或分页处理场景)

Get和Query

  • 核心功能:
    • Get:通过主键ID快速获取完整记录(如查询ID为0/1/2的记录)
    • Query:通过过滤表达式获取限定数量的结果(如color=”红色”取前5条)
  • 参数特点:
    • Get需明确指定ids字段列表
    • Query支持filter表达式和limit限制(示例:color like “color_1%”)

QueryIterator

  • 流式处理:
    • 通过iterator.next()分批返回结果(类似OpenAI API的流式响应)
    • 每批数量由batch_size参数控制(如每次返回5条记录)
  • 适用场景:
    • 处理大规模结果集(避免内存溢出)
    • 需要渐进式展示结果的场景(如分页加载)