Eson Wong's Blog

生活随想、学习笔记、读书总结、创作记录

0%

Milvus 入门教程

Milvus

Milvus 是一个开源的向量数据库,它是为了生成式 AI 的应用设计的。它支持大规模的向量检索。

Milvus 的发音是 /ˈmil vəs/。

本文将是 Milvus 的使用入门。

安装 Milvus

先准备好 Python 环境,然后使用 pip 安装 Milvus:

1
pip install -U pymilvus

使用 Milvus

创建一个本地的 Milvus 文件

1
2
3
from pymilvus import MilvusClient

client = MilvusClient("milvus_demo.db")

运行上面的代码,在当前目录下会生成一个名为 milvus_demo.db 的文件。

创建一个集合 Collection

我们通常把相关联的数据放在 Milvus 中的一个集合(Collection)中,我们可以把集合想象成一个传统数据库中的表。

下面的代码会创建一个集合,它存储的向量数据的的维度数是 768,这个维度数是接下来准备的向量数据的维度。

1
2
collection_name = "milvus_demo"
client.create_collection(collection_name, dimension=768)

为了避免重复创建 Collection,我们可以先检查 Collection 是否存在:

1
2
3
collection_name = "milvus_demo"
if not client.has_collection(collection_name):
client.create_collection(collection_name, dimension=768)

准备数据

pymilvus[model] python 库中提供了一些工具函数,可以帮助我们把文本数据转换成向量,来进行 Milvus 的学习。

下面会把hello world你好世界milvus is great这三个文本数据转换成向量数据:

1
2
3
4
5
6
7
8
from pymilvus import model

embedding_fn = model.DefaultEmbeddingFunction()
docs = ["hello world", "hi", "你好世界", "milvus is great"]

vectors = embedding_fn.encode_documents(docs)

print ("向量数据的维度:", len(vectors[0]))

我们会得到一个向量数据的列表,每个向量数据的维度是 768。

然后我们可以把向量数据和文本数据组合成由idvectortext组成的数据列表:

1
2
3
4
5
6
7
data = [
{"id": i, "vector": vectors[i], "text": docs[i]}
for i in range(len(vectors))
]

print("数据包含", len(data), "个条目,每个条目包含字段: ", data[0].keys())
print("vector 维度:", len(data[0]["vector"]))

插入数据

使用 insert(collection_name, data) 方法把列数据插入到 Milvus 的 milvus_demo 集合中:

1
2
response = client.insert(collection_name, data)
print(response)

此时我们插入了三条数据,每条数据包含了向量和原始文本。

检索数据

Retrieval Augmented Generation(RAG) 的应用场景中,通常要检索与输入文本最关度最高的文本数据。向量数据之间的关度可以通过计算向量之间的距离来衡量。

首先我们要把输入的数据转换成向量:

1
2
3
# 1.将要查询的数据转换为向量
query = "hi"
query_vectors = embedding_fn.encode_queries([query])

然后我们可以使用 search(collection_name, data) 方法来检索与输入文本在向量空间中最相近的数据:

1
2
3
4
5
6
7
8
# 2.向量查询
query_response = client.search(
collection_name,
data=query_vectors, # 查询向量
limit=2, # 返回的最大结果数
output_fields=["id", "text"], # 返回的字段
)
print(query_response)

我们会得到一个列表,列表中的每个元素包含了检索到的数据的iddistanceentity字段,其中distance字段表示检索到的数据与输入数据的距离。

1
2
3
4
5
data: ["[
{'id': 1, 'distance': 1.0, 'entity': {'text': 'hi', 'id': 1}},
{'id': 0, 'distance': 0.5280660390853882, 'entity': {'text': 'hello world', 'id': 0}},
{'id': 2, 'distance': 0.44701865315437317, 'entity': {'text': '你好世界', 'id': 2}}
]"]

distance 越接近 1,表示两个向量距离越近。从上面的结果中,我们可以看到,查询结果中的 hi 的与查询的文本相同,所以 distance 值为 1 。与查询文本hi距离最近的文本依次是hihello world你好世界。这意味着它们之间的相关度排序也是这样的。

删除数据

delete() 方法可以删除集合中的数据:

通过 id 删除数据:

1
client.delete(collection_name, ids=[1])

通过条件删除数据:

1
client.delete(collection_name, filter="id == 1")

删除集合

drop_collection() 方法可以删除集合:

1
client.drop_collection(collection_name)
请我喝杯咖啡吧!

欢迎关注我的其它发布渠道