向量数据库对比:Pinecone、Chroma、Weaviate架构与场景指南
向量数据库干的事情,说白了就是把Embedding——也就是文本、图像或者音频的数值表示——存下来,然后在查询的时候,从库里找出语义上最接近的结果。RAG系统能运转起来,靠的就是这个机制。下面拿三个主流的方案做个横向对比,每个都配了Python代码,文章里的代码都是结合长期生产环境的使用经验整理的。
大概的选型倾向是:生产级规模用Pinecone,本地快速原型用Chroma,需要混合搜索的时候,Wea viate是个不错的选项。
向量数据库究竟做了什么
给一段文本做Embedding,得到的其实是一个向量——比如说,一个由768个或者1536个数字组成的数组,它代表了这段文本的语义。语义相似的文本,生成的向量也是相似的。向量数据库把这些向量存下来并建立索引,目的就是支持快速的最近邻搜索。
当用户提出一个问题,先把问题也转成向量,然后向数据库发问:“库里哪些已存向量跟我最接近?”数据库返回语义上最相似的那些文本片段,这些片段随后会被注入到LLM的上下文中,帮助它生成更准确的回答。
检索这一步做得好坏,直接决定了RAG系统的整体表现。你如果能把检索这一步做到位,整个系统就能稳住;可要是这一步出了偏差,再好的大模型也只能给出自信却错误的答案。
Chroma:从原型开发开始
Chroma是一个开源方案,通过pip install chromadb就能装好。它支持本地内存运行,也可以持久化到磁盘上,最快5分钟就能搭出一个可用的向量存储。
基本Python设置长这样:
import chromadb
from chromadb.utils import embedding_functions
client = chromadb.PersistentClient(path='./my_db')
ef = embedding_functions.OpenAIEmbeddingFunction(
api_key='your-key', model_name='text-embedding-3-small')
collection = client.get_or_create_collection('docs', embedding_function=ef)
# 添加文档
collection.add(documents=['doc1 text', 'doc2 text'], ids=['id1','id2'])
# 查询
results = collection.query(query_texts=['your question'], n_results=5)
不过,Chroma天生不是云原生的。如果你想把服务扩展到多台机器,就得自己搭服务器来管理。一旦超出单机部署的范围,或者数据集规模超过大概100万条文档,就得考虑迁移了。如果当初接口设计得足够干净,这个过程倒也不算太痛苦,但总归要花时间。
Pinecone:进入生产环境时的选择
Pinecone是完全托管的云基础设施——你不需要自己跑服务器、不用操心内存管理,也不用管副本复制这些琐事。它的免费层大概能处理100万个1536维的向量,覆盖大多数小项目绰绰有余;付费层可以扩展到几十亿的规模。
基本Python设置:
from pinecone import Pinecone
pc = Pinecone(api_key='your-pinecone-api-key')
index = pc.Index('my-index')
# Upsert(需要单独处理 Embedding)
index.upsert(vectors=[('id1', embedding_vector, {'text': 'doc text'})])
# 查询
results = index.query(vector=query_embedding, top_k=5, include_metadata=True)
Pinecone的免费层确实够用。一旦超过限额,成本会随向量数量和查询量上升。一个日均1万次查询的初创应用,费用还在可控范围;但大规模应用下来,这笔支出就变得相当可观了。所以,从一开始就留好切换向量存储的余地很有必要——把检索逻辑封装在清晰的接口后面,以后想换方案也容易。
Wea viate:用于混合搜索
纯语义搜索和纯关键词搜索,都不是什么时候都好用的。语义搜索有时候会漏掉精确匹配,比如用户查"RFC 7519"的时候,关键词匹配明显比语义相似度更快定位到结果。混合搜索把余弦相似度和BM25关键词匹配结合起来,并对两者施加权重。
基本混合搜索代码:
import wea viate
client = wea viate.connect_to_wcs(cluster_url='…', auth_credentials=…)
collection = client.collections.get('Document')
# 混合查询:结合语义 + 关键词
results = collection.query.hybrid(
query='your question',
alpha=0.5, # 0 = 仅关键词, 1 = 仅语义, 0.5 = 均衡
limit=5
)
如果你的知识库里包含技术文档、API参考、或者带有特定标识符、型号、代码的内容,混合搜索的效果会明显优于纯语义检索。但如果内容很一般、偏通用文本,两者差距不大,为了混合搜索而引入额外复杂度,未必划算。
常见问题
第一个项目应该使用哪个向量数据库?
这个没什么悬念,就选Chroma。pip安装,本地就能跑,零配置,还免费。先用Chroma搭建第一个RAG系统,日后真需要扩展到生产环境,再迁移到Pinecone或者Wea viate——只要接口设计得干净,几个小时的迁移工作就够了。
做RAG一定需要向量数据库吗,还是可以用普通数据库?
PostgreSQL的pgvector扩展已经可以实现近似最近邻搜索,这是一个很可行的生产方案。Supabase(托管的Postgres)本身就原生支持pgvector,处理100万以下向量的小项目表现很好。规模再往上走,专用向量数据库在性能上的优势才会真正显现出来。
应该使用哪个Embedding模型?
OpenAI和Google的API都是可以选的,质量可靠,价格也便宜——大约每百万Token 0.02美元,生态支持也很广泛。如果是在本地部署且注重隐私的场景,通过Ollama运行nomic-embed-text是目前最好的免费方案;如果追求极限质量、不差钱,可以选text-embedding-3-large或者Cohere的embed-v3。