Spring AI(6)——向量存储

news2025/5/16 13:07:12

向量数据库是一种特殊类型的数据库,在 AI 应用中发挥着至关重要的作用。

在向量数据库中,查询与传统关系型数据库不同。它们执行的是相似性搜索,而非精确匹配。当给定一个向量作为查询时,向量数据库会返回与该查询向量“相似”的向量。

Spring AI 通过 VectorStore 接口提供了一个抽象的 API,用于与向量数据库交互。

VectorStore接口中主要方法:

public interface VectorStore extends DocumentWriter {

    default String getName() {
		return this.getClass().getSimpleName();
	}

    // 向向量数据库写入数据
    void add(List<Document> documents);

    // 根据id删除数据
    void delete(List<String> idList);

    // 根据过滤表达式删除数据
    void delete(Filter.Expression filterExpression);

    default void delete(String filterExpression) { ... };

    // 进行相似度搜索
    List<Document> similaritySearch(String query);

    List<Document> similaritySearch(SearchRequest request);

    default <T> Optional<T> getNativeClient() {
		return Optional.empty();
	}
}

支持的向量数据库:

  • Azure Vector Search
  • Apache Cassandra
  • Chroma Vector Store
  • Elasticsearch Vector Store
  • GemFire Vector Store
  • MariaDB Vector Store
  • Milvus Vector Store
  • MongoDB Atlas Vector Store
  • Neo4j Vector Store
  • OpenSearch Vector Store
  • Oracle Vector Store
  • PgVector Store
  • Pinecone Vector Store
  • Qdrant Vector Store
  • Redis Vector Store
  • SAP Hana Vector Store
  • Typesense Vector Store
  • Weaviate Vector Store
  • SimpleVectorStore - 一个简单的持久化向量存储实现,适合教学目的。

SimpleVectorStore使用

注意:需要提前启动上篇博客中通过Ollama安装的嵌入模型

SimpleVectorStore将向量数据存储在内存中。

导入jar

        <dependency>
            <groupId>org.springframework.ai</groupId>
            <artifactId>spring-ai-vector-store</artifactId>
        </dependency>

创建SimpleVectorStore对象

    @Bean
    public SimpleVectorStore vectorStore() {
        return SimpleVectorStore.builder(embeddingModel).build();
    }

创建对象时,将存储对象和嵌入模型进行关联。关于嵌入模型的使用,参考:

Spring AI(5)——通过嵌入模型进行数据的向量化处理-CSDN博客

向SimpleVectorStore对象中写入测试数据

本例中,创建Document对象时,三个参数分别为:文档id,文档内容,文档的元数据。

    @PostConstruct
    public void init() {
        List<Document> documents = List.of(
                new Document("1", "今天天气不错", Map.of("country", "郑州", "date", "2025-05-13")),
                new Document("2", "天气不错,适合旅游", Map.of("country", "开封", "date", "2025-05-15")),
                new Document("3", "去哪里旅游好呢", Map.of("country", "洛阳", "date", "2025-05-15")));


        // 存储数据
        simpleVectorStore.add(documents);
    }

通过调试可以看出, SimpleVectorStore对象中存储的原始文档信息和向量化后的数据。

进行相似度搜索

根据字符串内容进行搜索

    @GetMapping("/store")
    public String store(String message) {
        // 相似度检索
        List<Document> list= simpleVectorStore.similaritySearch("旅游");
        System.out.println(list.size());
        System.out.println(list.get(0).getText());

        return "success";
    }

通过调试可以看到,对所有的数据进行向量的相似度计算,并进行打分,计算结果按照score的降序排列 。

根据元数据过滤器进行搜索

使用字符串设置搜索条件

例如:

  • "country == 'BG'"

  • "genre == 'drama' && year >= 2020"

  • "genre in ['comedy', 'documentary', 'drama']"

SearchRequest request = SearchRequest.builder()
    .query("World")
    .filterExpression("country == 'Bulgaria'")
    .build();

使用Filter.Expression设置搜索条件

可以使用 FilterExpressionBuilder 创建 Filter.Expression 的实例。一个简单的示例如下:

FilterExpressionBuilder b = new FilterExpressionBuilder();
Expression expression = this.b.eq("country", "BG").build();

可以使用以下运算符构建复杂的表达式:

EQUALS: '=='
MINUS : '-'
PLUS: '+'
GT: '>'
GE: '>='
LT: '<'
LE: '<='
NE: '!='

可以使用以下运算符组合表达式:

AND: 'AND' | 'and' | '&&';
OR: 'OR' | 'or' | '||';

参考示例:

Expression exp = b.and(b.eq("genre", "drama"), b.gte("year", 2020)).build();

还可以使用以下运算符:

IN: 'IN' | 'in';
NIN: 'NIN' | 'nin';
NOT: 'NOT' | 'not';

参考示例:

Expression exp = b.and(b.in("genre", "drama", "documentary"), b.not(b.lt("year", 2020))).build();

测试案例: 

    @GetMapping("/store")
    public String store(String message) {
        // 相似度检索
        // List<Document> list = simpleVectorStore.similaritySearch("旅游");

        // 创建过滤器对象
        FilterExpressionBuilder b = new FilterExpressionBuilder();
        Filter.Expression filter = b.eq("country", "郑州").build();
        // Filter.Expression filter = b.and(b.eq("country", "郑州"), b.gte("date", "2025-05-15")).build();;
        // 创建搜索对象
        SearchRequest request = SearchRequest.builder()
                .query("旅游") // 搜索内容
                .filterExpression(filter) // 指定过滤器对象
                .build();
        List<Document> list = simpleVectorStore.similaritySearch(request);
        System.out.println(list.size());
        System.out.println(list.get(0).getText());

        return "success";
    }

删除数据

    @GetMapping("/store2")
    public String store2(String message) {
        // 删除数据
        simpleVectorStore.delete(List.of("3"));
        return "success";
    }

注意:也可以根据元数据过滤器进行删除,本文不再演示

 Milvus进行向量存储

关于milvus的介绍和环境安装,参考:

LangChain4j(16)——使用milvus进行向量存储-CSDN博客

注意:需要提前启动上篇博客中通过Ollama安装的嵌入模型

导入jar 

<dependency>
	<groupId>org.springframework.ai</groupId>
	<artifactId>spring-ai-starter-vector-store-milvus</artifactId>
</dependency>

yml配置

在原来的基础上,增加如下配置:

spring:
  ai:
    vectorstore:
      milvus:
        client:
          host: "localhost"
          port: 19530
        databaseName: "myai"
        collectionName: "vector_store"
        embeddingDimension: 768
        indexType: IVF_FLAT
        metricType: COSINE

该配置中指定了milvus的数据库名,collection名称,向量纬度,索引的类型,向量搜索的算法等,更多的属性设置可以参考官网:

属性描述默认值

spring.ai.vectorstore.milvus.database-name

要使用的 Milvus 数据库名称。

default

spring.ai.vectorstore.milvus.collection-name

用于存储向量的 Milvus Collection 名称

vector_store

spring.ai.vectorstore.milvus.initialize-schema

是否初始化 Milvus 后端

false

spring.ai.vectorstore.milvus.embedding-dimension

存储在 Milvus Collection 中的向量维度。

1536

spring.ai.vectorstore.milvus.index-type

为 Milvus Collection 创建的索引类型。

IVF_FLAT

spring.ai.vectorstore.milvus.metric-type

用于 Milvus Collection 的度量类型(Metric Type)。

COSINE

spring.ai.vectorstore.milvus.index-parameters

用于 Milvus Collection 的索引参数。

{"nlist":1024}

spring.ai.vectorstore.milvus.id-field-name

Collection 的 ID 字段名称

doc_id

spring.ai.vectorstore.milvus.is-auto-id

布尔标志,指示 ID 字段是否使用 auto-id

false

spring.ai.vectorstore.milvus.content-field-name

Collection 的内容字段名称

content

spring.ai.vectorstore.milvus.metadata-field-name

Collection 的元数据字段名称

metadata

spring.ai.vectorstore.milvus.embedding-field-name

Collection 的嵌入字段名称

embedding

spring.ai.vectorstore.milvus.client.host

主机名称或地址。

localhost

spring.ai.vectorstore.milvus.client.port

连接端口。

19530

spring.ai.vectorstore.milvus.client.uri

Milvus 实例的 URI

-

spring.ai.vectorstore.milvus.client.token

用作身份识别和认证目的的 Token。

-

spring.ai.vectorstore.milvus.client.connect-timeout-ms

客户端通道的连接超时值。超时值必须大于零。

10000

spring.ai.vectorstore.milvus.client.keep-alive-time-ms

客户端通道的 Keep-alive 时间值。Keep-alive 值必须大于零。

55000

spring.ai.vectorstore.milvus.client.keep-alive-timeout-ms

客户端通道的 Keep-alive 超时值。超时值必须大于零。

20000

spring.ai.vectorstore.milvus.client.rpc-deadline-ms

愿意等待服务器回复的截止时间。设置截止时间后,客户端在遇到由网络波动引起的快速 RPC 失败时将等待。截止时间值必须大于或等于零。

0

spring.ai.vectorstore.milvus.client.client-key-path

用于 TLS 双向认证的 client.key 路径,仅当 "secure" 为 true 时生效

-

spring.ai.vectorstore.milvus.client.client-pem-path

用于 TLS 双向认证的 client.pem 路径,仅当 "secure" 为 true 时生效

-

spring.ai.vectorstore.milvus.client.ca-pem-path

用于 TLS 双向认证的 ca.pem 路径,仅当 "secure" 为 true 时生效

-

spring.ai.vectorstore.milvus.client.server-pem-path

用于 TLS 单向认证的 server.pem 路径,仅当 "secure" 为 true 时生效。

-

spring.ai.vectorstore.milvus.client.server-name

设置 SSL 主机名检查的目标名称覆盖,仅当 "secure" 为 True 时生效。注意:此值会传递给 grpc.ssl_target_name_override

-

spring.ai.vectorstore.milvus.client.secure

保护此连接的授权,设置为 True 以启用 TLS。

false

spring.ai.vectorstore.milvus.client.idle-timeout-ms

客户端通道的空闲超时值。超时值必须大于零。

24h

spring.ai.vectorstore.milvus.client.username

此连接的用户名和密码。

root

spring.ai.vectorstore.milvus.client.password

此连接的密码。

milvus

通过attu创建collection

注意:collection中的字段名称使用的是上面属性中的默认名称:

spring.ai.vectorstore.milvus.id-field-name=doc_id

spring.ai.vectorstore.milvus.content-field-name=content
spring.ai.vectorstore.milvus.metadata-field-name=metadata
spring.ai.vectorstore.milvus.embedding-field-name=embedding

注入MilvusVectorStore对象

    @Resource
    private MilvusVectorStore milvusVectorStore;

添加测试数据

    @PostConstruct
    public void init() {
        List<Document> documents = List.of(
                new Document("今天天气不错", Map.of("country", "郑州", "date", "2025-05-13")),
                new Document("天气不错,适合旅游", Map.of("country", "开封", "date", "2025-05-15")),
                new Document("去哪里旅游好呢", Map.of("country", "洛阳", "date", "2025-05-15")));

        // 存储数据
        milvusVectorStore.add(documents);

    }

本例没有指定Document的id,id会随机生成

相似度搜索

    @GetMapping("/search")
    public String search(String message) {
        // 相似度检索
        List<Document> list = milvusVectorStore.similaritySearch("旅游");

        System.out.println(list.size());
        System.out.println(list.get(0).getText());

        return "success";
    }

    @GetMapping("/search5")
    public String search5(String message) {
        MilvusSearchRequest request = MilvusSearchRequest.milvusBuilder()
                .query("旅游")
                .topK(5)
                .similarityThreshold(0.7)
                .filterExpression("date == '2025-05-15'") // Ignored if nativeExpression is set
                //.searchParamsJson("{\"nprobe\":128}")
                .build();
        // 相似度检索
        List<Document> list = milvusVectorStore.similaritySearch(request);

        System.out.println(list.size());
        System.out.println(list.get(0).getText());

        return "success";
    }

top_k: 表示根据token排名,只考虑前k个token

similarity threshold:相似度的阈值

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

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

相关文章

【Matlab】最新版2025a发布,深色模式、Copilot编程助手上线!

文章目录 一、软件安装1.1 系统配置要求1.2 安装 二、新版功能探索2.1 界面图标和深色主题2.2 MATLAB Copilot AI助手2.3 绘图区升级2.4 simulink2.5 更多 延迟一个月&#xff0c;终于发布了&#x1f92d;。 一、软件安装 1.1 系统配置要求 现在的电脑都没问题&#xff0c;老…

uniapp,小程序中实现文本“展开/收起“功能的最佳实践

文章目录 示例需求分析实现思路代码实现1. HTML结构2. 数据管理3. 展开/收起逻辑4. CSS样式 优化技巧1. 性能优化2. 防止事件冒泡3. 列表更新处理 实际效果总结 在移动端应用开发中&#xff0c;文本内容的"展开/收起"功能是提升用户体验的常见设计。当列表项中包含大…

思维链框架:LLMChain,OpenAI,PromptTemplate

什么是思维链,怎么实现 目录 什么是思维链,怎么实现思维链(Chain of Thought)在代码中的实现方式1. 手动构建思维链提示2. 少样本思维链提示3. 自动思维链生成4. 思维链与工具使用结合5. 使用现有思维链框架:LLMChain,OpenAI,PromptTemplate思维链实现的关键要点思维链(C…

使用 QGIS 插件 OpenTopography DEM Downloader 下载高程数据(申请key教程)

使用 QGIS 插件 OpenTopography DEM Downloader 下载高程数据 目录 使用 QGIS 插件 OpenTopography DEM Downloader 下载高程数据&#x1f4cc; 简介&#x1f6e0; 插件安装方法&#x1f30d; 下载 DEM 数据步骤&#x1f511; 注册 OpenTopography 账号&#xff08;如使用 Cope…

计算机组成与体系结构:替换策略(MRU LRU PLRU LFU)

目录 &#x1f3b2; MRU&#xff08;最近最常使用&#xff09; &#x1fa9c; 操作流程&#xff1a; &#x1f3b2; LRU&#xff08;最近最少使用&#xff09; &#x1fa9c; 操作流程&#xff1a; 示例 &#x1f50d; Age Bits&#xff08;年龄位&#xff09; 核心思想…

websocket入门详解

入门websocket的基础应该掌握一下问题&#xff1a; 1、什么是握手&#xff1f; 2、什么是websocket&#xff1f; 3、websocket和http的区别&#xff0c;应用场景 4、html前端简单代码演示 5、springboot整合websocket使用 6、使用vueelementui打造简单聊天室 7、使用web…

(6)python开发经验

文章目录 1 QListWidget样式显示异常2 模块编码错误3 qtcreator开发pyqt编码错误 更多精彩内容&#x1f449;内容导航 &#x1f448;&#x1f449;Qt开发 &#x1f448;&#x1f449;python开发 &#x1f448; 1 QListWidget样式显示异常 main.py import sys from PySide6.QtWi…

HPC软件使用之ANSYS Fluent

目录 一、软件介绍 二、脚本编写 2.1 jou文件 2.2 slurm脚本文件 三、作业提交及查看 四、案例演示 4.1 网格模型 4.2 jou脚本 4.3 slurm脚本 4.4 计算 4.5 结果查看 从本文开始&#xff0c;我们将介绍如何在超级计算机上使用科学计算、工程仿真计算软件开展计算&am…

YOLO11解决方案之距离计算探索

概述 Ultralytics提供了一系列的解决方案&#xff0c;利用YOLO11解决现实世界的问题&#xff0c;包括物体计数、模糊处理、热力图、安防系统、速度估计、物体追踪等多个方面的应用。 测量两个物体之间的间距被称为特定空间内的距离计算&#xff0c;YOLO11使用两个边界框的中心…

论文学习_Precise and Accurate Patch Presence Test for Binaries

摘要&#xff1a;打补丁是应对软件漏洞的主要手段&#xff0c;及时将补丁应用到所有受影响的软件上至关重要&#xff0c;然而这一点在实际中常常难以做到&#xff0c;研究背景。因此&#xff0c;准确检测安全补丁是否已被集成进软件发行版本的能力&#xff0c;对于防御者和攻击…

Ascend的aclgraph(九)AclConcreteGraph:e2e执行aclgraph

1回顾 前面的几章内容探讨了aclgraph运行过程中的涉及到的关键模块和技术。本章节将前面涉及到的模块串联起来&#xff0c;对aclgraph形成一个端到端的了解。 先给出端到端运行的代码&#xff0c;如下&#xff1a; import torch import torch_npu import torchair import log…

c++从入门到精通(四)--动态内存,模板与泛型编程

文章目录 动态内存直接管理内存Shared_ptr类Unique_ptrWeak_ptr动态数组allocator类文本查询程序 模板与泛型编程定义模板函数模板类模板模板参数成员模板控制实例化 模板实参推断重载与模板可变参数模板模板特例化 动态内存 c中动态内存的管理是通过new和delete运算符来实现的…

寻找两个正序数组的中位数 - 困难

************* Python topic: 4. 寻找两个正序数组的中位数 - 力扣&#xff08;LeetCode&#xff09; ************* Give the topic an inspection. Do the old topic will give you some new sparks. Before that, I do some really good craetive things about my logo. …

国产密码新时代!华测国密 SSL 证书解锁安全新高度

在数字安全被提升到国家战略高度的今天&#xff0c;国产密码算法成为筑牢网络安全防线的关键力量。华测国密SSL证书凭借其强大性能与贴心服务&#xff0c;为企业网络安全保驾护航&#xff0c;成为符合国家安全要求的不二之选&#xff01;​ 智能兼容&#xff0c;告别浏览器适配…

【金仓数据库征文】从云计算到区块链:金仓数据库的颠覆性创新之路

目录 一、引言 二、金仓数据库概述 2.1 金仓数据库的背景 2.2 核心技术特点 2.3 行业应用案例 三、金仓数据库的产品优化提案 3.1 性能优化 3.1.1 查询优化 3.1.2 索引优化 3.1.3 缓存优化 3.2 可扩展性优化 3.2.1 水平扩展与分区设计 3.2.2 负载均衡与读写分离 …

股指期货套期保值怎么操作?

股指期货套期保值就是企业或投资者通过持有与其现货市场头寸相反的期货合约&#xff0c;来对冲价格风险的一种方式。换句话说&#xff0c;就是你在股票市场上买了股票&#xff08;现货&#xff09;&#xff0c;担心股价下跌会亏钱&#xff0c;于是就在期货市场上卖出相应的股指…

基于IBM BAW的Case Management进行项目管理示例

说明&#xff1a;使用IBM BAW的难点是如何充分利用其现有功能根据实际业务需要进行设计&#xff0c;本文是示例教程&#xff0c;因CASE Manager使用非常简单&#xff0c;这里重点是说明如何基于CASE Manager进行项目管理&#xff0c;重点在方案设计思路上&#xff0c;其中涉及的…

黑马k8s(七)

1.Pod介绍 查看版本&#xff1a; 查看类型,这里加s跟不加s没啥区别&#xff0c;可加可不加 2.Pod基本配置 3.镜像拉去策略 本地没有这个镜像&#xff0c;策略是Never&#xff0c;启动失败 查看拉去策略&#xff1a; 更改拉去策略&#xff1a; 4.启动命令 运行的是nginx、busv…

九、HQL DQL七大查询子句

作者&#xff1a;IvanCodes 日期&#xff1a;2025年5月15日 专栏&#xff1a;Hive教程 Apache Hive 的强大之处在于其类 SQL 的查询语言 HQL&#xff0c;它使得熟悉 SQL 的用户能够轻松地对存储在大规模分布式系统&#xff08;如 HDFS&#xff09;中的数据进行复杂的查询和分析…

RTSP 播放器技术探究:架构、挑战与落地实践

RTSP 播放器为什么至今无法被淘汰&#xff1f; 在实时视频传输领域&#xff0c;RTSP&#xff08;Real-Time Streaming Protocol&#xff09;作为最基础、最常见的协议之一&#xff0c;至今依然被广泛用于监控设备、IP Camera、视频服务器等设备中。然而&#xff0c;要构建一个稳…