Faiss向量数据库

Faiss(Facebook AI Similarity Search)向量数据库是由Facebook AI研究院开发的一种高效相似性搜索和聚类的库。Faiss不仅支持在高维空间中进行高效的相似性搜索,还能够在处理大规模数据集时展现出卓越的性能,尤其适用于图像检索、文本搜索、推荐系统和语音处理等多种应用场景。 

  • 在推荐系统中,Faiss可以用于快速查找用户可能感兴趣的物品或寻找具有相似兴趣的用户。 
  • 在信息检索领域,Faiss可以用于构建文档或图像的相似性搜索引擎。
  • 在图像识别领域,Faiss可以用于构建图像特征的索引,实现快速的相似图像搜索和图像聚类。

 安装Faiss:

💢cpu版本:

conda install -c pytorch faiss-cpu

💢gpu版本:

conda install -c pytorch faiss-gpu

Faiss 处理固定维数 d 的向量集合,通常为几十到几百个。这些集合可以存储在矩阵中。我们假设采用行主存储,即向量编号 i 的第 j 个分量存储在矩阵的第 i 行、第 j 列中。Faiss 仅使用 32 位浮点矩阵。

import numpy as np
d = 64                           # 设置向量的维度为64
nb = 100000                      # 向量数量为100,000
nq = 10000                       # 查询向量的数量为10,000
np.random.seed(1234)             # make reproducible
xb = np.random.random((nb, d)).astype('float32')
xb[:, 0] += np.arange(nb) / 1000.
xq = np.random.random((nq, d)).astype('float32')
xq[:, 0] += np.arange(nq) / 1000.    # 修改查询向量的第一个维度

建立索引 

Faiss 是围绕Index对象构建的。它封装了一组数据库向量,并可选地对它们进行预处理,以提高搜索效率。索引有很多种类型,我们将使用最简单的版本,即对它们进行强力的 L2 距离搜索:IndexFlatL2

所有索引在构建时都需要知道它们所操作的向量的维数,当索引建立并训练完成后,可以对索引进行两种操作:addsearch

  • 当我们说一个索引是否被“训练”时,我们实际上是指该索引是否已经通过某种方式优化了其内部结构,以便更有效地处理搜索查询。 
import faiss                   
index = faiss.IndexFlatL2(d)   # 创建一个IndexFlatL2类型的索引
print(index.is_trained)        # 打印出索引是否已经被训练
index.add(xb)                  # 将向量添加到索引中
print(index.ntotal)
  • IndexFlatL2索引是一种简单的暴力搜索索引,它不需要训练过程,因为它直接计算查询向量与数据库中所有向量的L2距离,以找到最相似的向量。 

 

搜索~

可以在索引上执行的基本搜索操作是k最近邻搜索,即对于每个查询向量,k在数据库中找到其最近的邻居。

此操作的结果可以方便地存储在大小为nq-by-的整数矩阵中k,其中第 i 行包含查询向量 i 的邻居的 ID,按距离递增排序。除了这个矩阵之外,该search操作还返回一个nq-by-k浮点矩阵,其中包含相应的平方距离。

k = 4                          # we want to see 4 nearest neighbors
D, I = index.search(xb[:5], k) # 在索引中搜索xb数组的前5个向量(xb[:5])的k个最近邻居
print(I)
print(D)
D, I = index.search(xq, k)     # 整个查询集xq上搜索每个查询向量的k个最近邻居
print(I[:5])                   # 前5个查询向量的最近邻居的索引位置
print(I[-5:])   
  • D:包含了查询向量与其找到的最近邻居之间的距离。 
  • I:也是一个数组,但它包含的是最近邻居在索引中的位置或索引。

结果:


 

💥由于索引中未添加任何向量,因此无法进行有效的相似性搜索。在实际应用中,我们需要先将向量添加到索引中,然后才能进行搜索操作。


💥向索引添加向量:

nb = 100000  # 假设有100,000个向量  
xb = np.random.random((nb, d)).astype('float32')  # 生成随机向量数据,100000个64维数据
index.add(xb)  # 将向量数据添加到索引中
# 优化索引(跳过)

💯结果:

  •  后两个为实际的搜索输出(前五和后五)。

更快的搜索!

为了加快搜索速度,可以将数据集分割成块。我们在 d 维空间中定义 Voronoi 单元,每个数据库向量都位于其中一个单元中。在搜索时,仅将查询 x 所在的单元中包含的数据库向量 y 和一些相邻的向量与查询向量进行比较。

这是通过IndexIVFFlat索引完成的。这种类型的索引需要一个训练阶段,可以对具有与数据库向量相同分布的任何向量集合执行。

IndexIVFFlat需要另一个索引,即量化器,它将向量分配给 Voronoi 单元。每个单元由一个质心定义,找到向量所在的 Voronoi 单元就是在质心集合中找到向量的最近邻居。这是另一个索引的任务,通常是IndexFlatL2

nlist = 100
# nlist指定IndexIVFFlat索引中聚类中心的数量
k = 4
quantizer = faiss.IndexFlatL2(d)  
index = faiss.IndexIVFFlat(quantizer, d, nlist)
# 这个索引中,quantizer 被用作内部机制来量化向量,并将它们分配到倒排文件中的不同聚类中心# assert 语句用于验证索引的状态,确保其在训练前后的行为符合预期。
assert not index.is_trained
index.train(xb)
print("~~训练完成~~")
assert index.is_trained
index.add(xb)                  
D, I = index.search(xq, k)     
print(I[-5:])                  
index.nprobe = 10              # 在搜索时控制要检查的聚类中心的数量
D, I = index.search(xq, k)
print(I[-5:])       # quantizer 被“嵌入”到 index 中,是因为 index 需要使用 quantizer 的量化功能来将向量分配到正确的聚类中心,并实现高效的搜索。
  • ⭐️IndexIVFFlat索引首先将向量空间划分为nlist个聚类中心,然后使用quantizerIndexFlatL2索引)来量化这些中心。
  • ⭐️在搜索时,IndexIVFFlat索引会先确定查询向量所属的聚类中心,然后只在该中心的向量中执行搜索,从而大大减少了计算量。
  • ⭐️xb(代表数据集的一部分或全部)来训练索引。这是为了优化量化器或聚类中心。
  • ⭐️我们重新初始化了索引 index,所以第一次添加的操作就没有影响了。
  • 🌟每创建一个索引,就相当于在向量搜索的上下文中创建了一个独立的、用于存储和查询向量的数据结构。

搜索方法有两个参数:nlist,即单元格数量,以及nprobe,即执行搜索时访问的单元格数量(共nlist

🧊nprobe = 10: 

🧊nprobe = 1 :

💢设置 nprobe = nlist 会得到与强力搜索相同的结果(但速度较慢)。 

Faiss支持将索引保存到磁盘文件中,并在需要时重新加载它们。通过保存和重新加载索引,可以在不同的会话或应用程序中重用索引:

# 保存索引  
faiss.write_index(index, 'index.faiss')  # 加载索引  
index = faiss.read_index('index.faiss')

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/1522243.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

C++和蓝图混用事件

一、在C中创建动态多播委托 1、UEBpAndCpp_Sender.h //声明一个蓝图可调用的多播委托的类型DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FUEBpAndCpp_Broadcast, int, Param);//创建对象UPROPERTY(BlueprintAssignable)FUEBpAndCpp_Broadcast UEBpAndCpp_Broadcast;注意&…

Vue3其他Api

1.shallowRef与shallowReactive <template><div class"app"><h2>求和为:{{ sum }}</h2><h2>名字为:{{ person.name }}</h2><h2>年龄为:{{ person.age }}</h2><button click"sum 1">sum1</butto…

深入浅出:模拟实现 C++ STL 中的 unordered_map 和 unordered_set

目录 引言基础知识 散列表哈希函数负载因子模拟实现 unordered_set 数据结构设计哈希函数碰撞解决策略插入操作查找操作删除操作模拟实现 unordered_map 键值对存储插入操作查找操作删除操作代码示例总结 1. 引言 unordered_map 和 unordered_set 是 C 标准模板库 (STL) 中非…

LeetCode: 543. 二叉树的直径

二叉树的直径 原题 给你一棵二叉树的根节点&#xff0c;返回该树的 直径 。 二叉树的 直径 是指树中任意两个节点之间最长路径的 长度 。这条路径可能经过也可能不经过根节点 root 。 两节点之间路径的 长度 由它们之间边数表示。 示例 1&#xff1a; 输入&#xff1a;roo…

Vulnhub:hacksudo search

靶机下载地址。下载完成后&#xff0c;在VirtualBox中导入虚拟机&#xff0c;系统处理器修改为2&#xff0c;网卡配置修改为桥接。 信息收集 主机发现 扫描攻击机同网段存活主机。 nmap 192.168.31.0/24 -Pn -T4 靶机ip&#xff1a;192.168.31.218 端口扫描 nmap 192.168…

大数据采集迁移工具

Flume Sqoop kafka框架 MQ&#xff1a;消息队列 broker相当于服务器 消息队列

视频化时代,用好AIGC产品赋能企业培训打造增效降本“最佳实践”

根据IBM的数据&#xff0c;85%的中国企业正在加速投资AI领域&#xff0c;其中超过63%的企业已积极采用生成式AI。德勤的调研进一步显示&#xff0c;近80%的全球受访企业高管认为&#xff0c;生成式AI的兴起与发展将在3年内推动组织和行业发生实质性变革&#xff0c;这也就意味着…

2024爆火全网大模型书籍:《从零构建大型语言模型》星标17.8k

2024爆火全网大模型书籍&#xff1a;《从零构建大型语言模型》星标17.8k 近期&#xff0c;机器学习和 AI 研究员、畅销书《Python 机器学习》作者 Sebastian Raschka 又写了一本新书 ——《Build a Large Language Model (From Scratch)》&#xff0c;旨在讲解从头开始构建大型…

线性代数 -- 矩阵求导

Tips&#xff1a;本文为理解神经网络的前置知识&#xff0c;整体内容并不全&#xff0c;相关内容还需后续进一步完善。 一、基础 1、标量、向量和矩阵 标量&#xff1a;只有大小&#xff0c;没有方向的量 向量&#xff08;欧几里得向量&#xff09;&#xff1a;具有大小和方向…

数仓建模:一文带你读懂什么是数仓建模? | 详聊数据建模的几种形式

目录 1 数据仓库的特点和意义 1.1 数仓特点 1.2 数仓形态演进 1.3 数仓建模的意义 1.4 数仓价值 2 数仓建模流派之争 2.1 Inmon数仓架构 2.2 Kimball数仓架构 2.3 两种建模方式对比分析 3 数仓建模流程 3.1 整体流程 3.2 数仓建模三步调研 3.3 业务流程构建 3.4 领…

MySQL的服务器与客户端:架构解析与实践

文章目录 MySQL的服务器和客户端服务端处理客户端请求连接管理解析与优化查询缓存语法解析查询优化 存储引擎不同的存储引擎查看支持的存储引擎为不同的表设置存储引擎 MySQL是一个广泛使用的开源关系数据库管理系统&#xff0c;其核心架构由服务器端和客户端两大部分组成。本文…

Tableau 社区项目 | 参与 Data+TV 挑战,洞悉全球电视剧集数据的精彩故事!

如果你钟爱某部电视剧集&#xff0c;正苦于没有数据练手&#xff0c;就快来参与 DataTV 挑战吧~ 去年&#xff0c;Tableau 和 IMDb 携手发起 DataMovies 挑战&#xff0c;吸引了全球各地的数据爱好者与影迷参与。今年&#xff0c;TC24 Viz 竞赛也以此为主题&#xff0c;让我们领…

LLM大模型学习路径指南速成,两月学完

大家好&#xff01;整理了一些我的大模型学习路线和参考资料&#xff0c;供初学者入门了解和实践 以下是简化版的学习路线&#xff1a; 第1周&#xff1a;基础知识储备 了解人工智能和大模型的基本概念。 学习线性代数、概率论和统计学的基本知识。 掌握Python编程基础。 第2…

获取响应头Content-Disposition,提取文件名

// 响应头数据&#xff0c;这里使用假数据 const temp "attachement;filename%%%%%%......."// 处理文件名的正则校验let filenameRegex /filename[^;\n]*((["]).*?\2|[^;\n]*)/;let matches filenameRegex.exec(temp);let fileName "批量下载.pdf&qu…

【论文分享】sNPU: Trusted Execution Environments on Integrated NPUs 24‘ISCA

目录 AbstractINTRODUCTIONBACKGROUND AND RELATED WORKTrusted Execution Environment (TEE)Neural Processing Unit (NPU)Integrated NPU v.s. Discrete NPU Multi-tasking Requirements for NPUsLow NPU utilization for a single ML workloadSimultaneous execution of bot…

两行代码开启大模型评测之旅!OpenCompass 工具版本全面更新,快来试试看

作为 OpenCompass 司南大模型评测体系三大核心模块之一的评测工具链体系 CompassKit 近日迎来重大更新&#xff01;​ 本次更新主要集中在 OpenCompass 大语言模型评测工具&#xff0c;主要带来了以下几大新功能&#xff0c;欢迎大家使用&#xff01;​ 基于 pip 的一键安装&a…

分类预测|基于CNN-LSTM-Attention卷积-长短时记忆-注意力数据分类Matlab程序 直接运行程序或替换数据集运行程序

分类预测|基于CNN-LSTM-Attention卷积-长短时记忆-注意力数据分类Matlab程序 直接运行程序或替换数据集运行程序 文章目录 一、基本原理1. 卷积神经网络&#xff08;CNN&#xff09;CNN的基本步骤&#xff1a; 2. 长短期记忆网络&#xff08;LSTM&#xff09;LSTM的基本步骤&am…

屏幕像素初步认识

屏幕分辨率&#xff1a; 屏幕分辨率是指显示器所能显示的像素的总数&#xff0c;通常以水平像素数乘以垂直像素数来表示&#xff0c;例如1920x1080。这个数字越大&#xff0c;屏幕显示的图像就越清晰&#xff0c;细节展现得也更加丰富。 像素&#xff08;Pixel&#xff09;&am…

【Linux】使用Linux实现小程序 - 进度条

目录 一、缓冲区二、回车换行的概念三、进度条的设计3.1 版本1&#xff08;没有配合场景&#xff09;3.2 版本2&#xff08;配合场景&#xff09;3.3 版本3&#xff08;美化进度条&#xff09; 结尾 一、缓冲区 C/C语言&#xff0c;会针对标准输出&#xff0c;给我们提供默认的…

【转变之旅】从程序员到AI绘画艺术家,我的月入过万之路

曾经&#xff0c;我的生活平淡如水&#xff0c;作为一名程序员&#xff0c;每天重复着朝九晚五的工作。然而&#xff0c;一场突如其来的裁员&#xff0c;让我陷入了失业的深渊。为了生活&#xff0c;我选择了开滴滴谋生。没想到&#xff0c;这个看似权宜之计的决定&#xff0c;…