当前位置: 首页 > news >正文

Milvus:向现有Collections更改和添加字段(十一)

一、更改集合字段属性

1.1 概述

Milvus 支持对现有集合的部分字段属性进行调整,核心用于优化列约束或强化数据完整性。但存在明确操作限制,需提前知晓:
  • 不可更改字段:主键字段、分区键字段(一旦设置永久固定);向量字段(维度等核心属性无法修改)。
  • 可更改范围:仅支持对 VARCHAR 字段、ARRAY 字段的特定属性,以及字段级 mmap 设置进行调整。

1.2 更改 VARCHAR 字段的 max_length

功能说明
VARCHAR 字段的 max_length 定义了字符串的最大允许长度,当业务场景中需要存储更长的字符串(如从 200 字符扩展到 1024 字符)时,可通过该操作调整,且仅支持增大长度,不支持缩小。
代码详解
from pymilvus import MilvusClientdef alter_varchar_field():"""更改 VarChar 字段的最大长度"""# 1. 初始化 Milvus 客户端,建立与 Milvus 服务的连接# uri:Milvus 服务的地址和端口(默认本地端口 19530)# token:认证凭证,格式为 "用户名:密码"(默认用户 root,密码 Milvus)client = MilvusClient(uri="http://localhost:19530",token="root:Milvus")# 2. 调用 alter_collection_field 方法修改字段属性client.alter_collection_field(collection_name="my_collection",  # 目标集合名称(需提前存在)field_name="varchar",  # 要修改的 VARCHAR 类型字段名field_params={"max_length": 1024  # 新的最大长度(需大于原有值,否则报错)})print("VarChar 字段最大长度更改成功")# 执行函数完成修改
alter_varchar_field()

1.3 更改 ARRAY 字段的 max_capacity

功能说明

ARRAY 字段的 max_capacity 表示数组可容纳的最大元素个数,例如原本限制 32 个元素的数组,可扩展为 64 个。需注意:仅能修改容量上限,无法改变数组内元素的数据类型(如从 INT64 改为 FLOAT)。

代码详解
def alter_array_field():"""更改 ARRAY 字段的最大容量"""# 初始化客户端(与 VARCHAR 字段修改的连接逻辑一致)client = MilvusClient(uri="http://localhost:19530",token="root:Milvus")# 修改 ARRAY 字段的最大容量client.alter_collection_field(collection_name="my_collection",  # 目标集合名称field_name="array",  # 要修改的 ARRAY 类型字段名field_params={"max_capacity": 64  # 新的数组最大容量(需大于原有值)})print("ARRAY 字段最大容量更改成功")# 执行函数
alter_array_field()

1.4 更改字段级 mmap 设置

功能说明

mmap(内存映射)是一种 I/O 优化机制,启用后字段数据会通过内存映射文件加载,减少内存占用并提升大文件读取效率,适用于存储大量文档片段、日志等数据的字段(如示例中的 doc_chunk 字段)。

代码详解
def alter_field_mmap():"""更改字段的内存映射设置"""# 初始化客户端client = MilvusClient(uri="http://localhost:19530",token="root:Milvus")# 启用字段的内存映射(也可设置为 False 关闭)client.alter_collection_field(collection_name="my_collection",  # 目标集合名称field_name="doc_chunk",  # 要设置的字段名(通常为大体积数据字段)field_params={"mmap.enabled": True}  # 启用 mmap,关闭则设为 False)print("字段 mmap 设置更改成功")# 执行函数
alter_field_mmap()

二、向现有集合添加字段

2.1 前提条件和限制

支持添加的字段类型
仅支持添加标量及结构化字段,具体包括:
  • 整数类型:INT8、INT16、INT32、INT64
  • 浮点类型:FLOAT、DOUBLE
  • 字符串类型:VARCHAR
  • 布尔类型:BOOL
  • 数组类型:ARRAY
  • JSON 类型:JSON
不支持添加的字段类型
  • 向量字段:FLOAT_VECTOR、BINARY_VECTOR 等(向量字段仅能在集合创建时定义)
  • 主键字段、分区键字段(需在集合初始化时设置,不可后续添加)
  • 动态字段($meta,无法通过添加该字段启用动态功能)
其他核心限制
  • 新字段必须设置为可空(nullable=True),因现有数据无该字段值,默认填充为 NULL
  • 字段名需唯一,不可与集合中已存在的字段重名
  • 每个集合的字段总数有上限(取决于 Milvus 版本,通常不超过 1024 个)
  • 不可通过添加 $meta 字段启用动态字段功能,需在集合创建时设置 enable_dynamic_field=True

2.2 基础用法

功能说明
为后续添加字段的演示做准备,创建一个包含主键、向量字段和 VARCHAR 字段的基础集合,并插入测试数据,模拟真实业务中的现有集合场景。
代码详解
from pymilvus import MilvusClient, DataTypedef setup_base_collection():"""创建基础集合用于演示添加字段操作"""# 1. 初始化 Milvus 客户端(本地无认证时可省略 token 参数)client = MilvusClient(uri="http://localhost:19530")# 2. 创建集合 Schema(数据结构定义)schema = client.create_schema(auto_id=False,  # 关闭自动生成主键,手动指定 id 字段enable_dynamic_field=False,  # 关闭动态字段功能,仅使用静态字段)# 3. 向 Schema 中添加字段# 主键字段:id(INT64 类型,必须设为 is_primary=True)schema.add_field(field_name="id", datatype=DataType.INT64, is_primary=True)# 向量字段:vector(FLOAT_VECTOR 类型,维度为 128)schema.add_field(field_name="vector", datatype=DataType.FLOAT_VECTOR, dim=128)# VARCHAR 字段:title(最大长度 200)schema.add_field(field_name="title", datatype=DataType.VARCHAR, max_length=200)# 4. 创建集合(根据 Schema 定义在 Milvus 中创建物理集合)client.create_collection(collection_name="demo_collection",  # 集合名称schema=schema  # 关联上述定义的 Schema)# 5. 插入测试数据(模拟现有业务数据)test_data = [{"id": 1, "vector": [0.1]*128, "title": "Document 1"},  # vector 为 128 个 0.1 组成的列表{"id": 2, "vector": [0.2]*128, "title": "Document 2"},{"id": 3, "vector": [0.3]*128, "title": "Document 3"}]client.insert(collection_name="demo_collection", data=test_data)print("基础集合创建并初始化完成")return client  # 返回客户端实例,供后续添加字段使用# 执行函数,获取客户端对象
client = setup_base_collection()

2.3 场景 1:快速添加可空字段

功能说明

适用于需要快速扩展字段,且无需默认值的场景(如添加时间戳、分类、浏览量等辅助字段),现有数据的新字段值默认为 NULL,新插入数据可选择性填充。

代码详解
def add_nullable_fields():"""添加可空字段到现有集合"""print("=== 添加可空字段演示 ===")# 1. 添加时间戳字段(记录数据创建时间,INT64 类型存储时间戳)client.add_collection_field(collection_name="demo_collection",  # 目标集合(已创建的基础集合)field_name="created_timestamp",  # 新字段名(唯一)data_type=DataType.INT64,  # 字段类型(整数类型)nullable=True  # 必须设为 True,否则报错)print("✓ 添加 created_timestamp 字段")# 2. 添加分类字段(存储数据所属分类,VARCHAR 类型)client.add_collection_field(collection_name="demo_collection",field_name="category",data_type=DataType.VARCHAR,max_length=50,  # VARCHAR 字段必须指定 max_lengthnullable=True)print("✓ 添加 category 字段")# 3. 添加数值字段(存储浏览量,INT64 类型)client.add_collection_field(collection_name="demo_collection",field_name="view_count",data_type=DataType.INT64,nullable=True)print("✓ 添加 view_count 字段")# 验证字段添加结果:查询现有数据,查看新字段值(均为 NULL)print("\n验证现有数据的新字段值:")results = client.query(collection_name="demo_collection",filter="",  # 无筛选条件,查询所有数据output_fields=["id", "created_timestamp", "category", "view_count"],  # 包含新添加的字段limit=3  # 限制返回 3 条数据)# 遍历输出结果for result in results:print(f"ID: {result['id']}, "f"Timestamp: {result.get('created_timestamp')}, "  # 现有数据无该值,返回 Nonef"Category: {result.get('category')}, "f"ViewCount: {result.get('view_count')}")# 执行函数添加字段
add_nullable_fields()

2.4 场景 2:添加带默认值的字段

功能说明

适用于需要为新字段设置统一默认值的场景(如数据状态、优先级等),现有数据会自动填充默认值,新插入数据可覆盖默认值,确保数据一致性。

代码详解
def add_fields_with_defaults():"""添加带默认值的字段"""print("\n=== 添加带默认值的字段演示 ===")# 1. 添加带默认字符串值的字段(状态字段,默认值为 "active")client.add_collection_field(collection_name="demo_collection",field_name="status",data_type=DataType.VARCHAR,max_length=20,  # 字符串最大长度nullable=True,  # 仍需设为可空(允许手动设置为 NULL)default_value="active"  # 设置默认值为字符串 "active")print("✓ 添加 status 字段(默认值: 'active')")# 2. 添加带默认数值的字段(优先级字段,默认值为 1)client.add_collection_field(collection_name="demo_collection",field_name="priority",data_type=DataType.INT32,  # 32 位整数类型nullable=True,default_value=1  # 默认值为整数 1)print("✓ 添加 priority 字段(默认值: 1)")# 3. 添加带默认布尔值的字段(是否发布字段,默认值为 False)client.add_collection_field(collection_name="demo_collection",field_name="is_published",data_type=DataType.BOOL,  # 布尔类型(True/False)nullable=True,default_value=False  # 默认值为 False)print("✓ 添加 is_published 字段(默认值: False)")# 验证默认值应用:查询现有数据,新字段已填充默认值print("\n验证默认值应用:")results = client.query(collection_name="demo_collection",filter="",output_fields=["id", "status", "priority", "is_published"],limit=3)for result in results:print(f"ID: {result['id']}, "f"Status: '{result.get('status')}', "  # 输出默认值 "active"f"Priority: {result.get('priority')}, "  # 输出默认值 1f"Published: {result.get('is_published')}")  # 输出默认值 False# 执行函数添加带默认值的字段
add_fields_with_defaults()

2.5 插入新数据验证字段行为

功能说明

添加字段后,验证新插入数据对新字段的处理逻辑:可手动指定字段值(覆盖默认值),也可省略字段(使用默认值),确保字段添加后的兼容性。

代码详解
def insert_new_data_after_adding_fields():"""在添加字段后插入新数据,验证字段行为"""print("\n=== 插入新数据验证字段行为 ===")# 定义新数据:包含原有字段和所有新字段new_data = [{"id": 4,  # 主键(需唯一,不与现有数据冲突)"vector": [0.4]*128,  # 向量字段(必填,与集合维度一致)"title": "New Document 4",  # 原有 VARCHAR 字段# 新添加的可空字段:手动指定值"created_timestamp": 1672531200,  # 时间戳(2023-01-01 00:00:00)"category": "technology",  # 分类"view_count": 150,  # 浏览量# 新添加的带默认值字段:手动指定值(覆盖默认值)"status": "published",  # 覆盖默认值 "active""priority": 2,  # 覆盖默认值 1"is_published": True  # 覆盖默认值 False},{"id": 5,"vector": [0.5]*128,"title": "New Document 5",# 部分新字段:手动指定值"created_timestamp": 1672617600,  # 时间戳(2023-01-02 00:00:00)"category": "science","view_count": 75,# 带默认值的字段:省略,使用默认值(status="active"、priority=1、is_published=False)}]# 插入新数据到集合client.insert(collection_name="demo_collection", data=new_data)print("✓ 新数据插入成功")# 验证新数据:查询 ID 为 4 和 5 的数据,查看字段值print("\n新插入数据验证:")results = client.query(collection_name="demo_collection",filter="id in [4, 5]",  # 筛选条件:只查询 ID 4 和 5 的数据output_fields=["id", "title", "status", "priority", "is_published"])for result in results:print(f"ID: {result['id']}, "f"Title: {result['title']}, "f"Status: '{result.get('status')}', "  # ID4 为 "published",ID5 为 "active"f"Priority: {result.get('priority')}, "  # ID4 为 2,ID5 为 1f"Published: {result.get('is_published')}")  # ID4 为 True,ID5 为 False# 执行函数插入新数据并验证
insert_new_data_after_adding_fields()

三、高级场景:动态字段与静态字段的交互

3.1 创建支持动态字段的集合

功能说明

动态字段允许在插入数据时灵活添加未在 Schema 中定义的字段(无需提前声明),适用于字段不固定的场景(如产品属性、用户画像等)。需在集合创建时设置 enable_dynamic_field=True 启用该功能。

代码详解
def create_dynamic_field_collection():"""创建支持动态字段的集合"""# 初始化客户端client = MilvusClient(uri="http://localhost:19530")# 创建 Schema,启用动态字段功能schema = client.create_schema(auto_id=False,  # 手动指定主键enable_dynamic_field=True,  # 关键配置:启用动态字段)# 添加静态字段(必须提前定义的核心字段)schema.add_field(field_name="id", datatype=DataType.INT64, is_primary=True)  # 主键schema.add_field(field_name="vector", datatype=DataType.FLOAT_VECTOR, dim=128)  # 向量字段schema.add_field(field_name="name", datatype=DataType.VARCHAR, max_length=100)  # 静态 VARCHAR 字段# 创建集合client.create_collection(collection_name="dynamic_demo",  # 集合名称schema=schema)# 插入包含动态字段的数据dynamic_data = [{"id": 1,"vector": [0.1]*128,"name": "Product A",  # 静态字段# 动态字段:未在 Schema 中定义,直接插入"extra_info": "Dynamic field value",  # 字符串类型动态字段"score": 95.5,  # 浮点类型动态字段"tags": ["new", "featured"]  # 数组类型动态字段}]client.insert(collection_name="dynamic_demo", data=dynamic_data)print("动态字段集合创建并初始化完成")return client  # 返回客户端,供后续操作使用# 执行函数,创建动态字段集合并获取客户端
dynamic_client = create_dynamic_field_collection()

3.2 添加与动态字段同名的静态字段

功能说明

当动态字段需要转为固定结构(如需要索引、严格类型约束)时,可添加与动态字段同名的静态字段,后续插入数据需遵循静态字段的类型定义,原动态字段数据仍可通过 $meta 访问。

代码详解
def add_static_field_over_dynamic():"""添加与动态字段同名的静态字段,实现动态转静态"""print("\n=== 动态字段与静态字段交互演示 ===")# 添加静态字段:字段名与动态字段 "extra_info" 同名dynamic_client.add_collection_field(collection_name="dynamic_demo",  # 动态字段集合名称field_name="extra_info",  # 与动态字段同名data_type=DataType.INT64,  # 静态字段类型(可与动态字段类型不同,原动态字段为字符串)nullable=True  # 必须设为可空)print("✓ 添加 extra_info 静态字段")# 插入新数据:需遵循静态字段的类型约束new_dynamic_data = [{"id": 2,"vector": [0.2]*128,"name": "Product B",  # 静态字段"extra_info": 100,  # 必须符合静态字段类型(INT64),否则报错"score": 88.0,  # 仍为动态字段(未创建同名静态字段)"tags": ["sale", "hot"]  # 仍为动态字段}]dynamic_client.insert(collection_name="dynamic_demo", data=new_dynamic_data)print("✓ 新数据插入成功")# 执行函数,添加同名静态字段并插入数据
add_static_field_over_dynamic()

3.3 查询静态字段和动态字段的值

功能说明

添加同名静态字段后,查询时默认返回静态字段值,原动态字段值需通过 $meta [' 字段名 '] 显式查询,支持同时获取静态和动态字段值,确保数据不丢失。

代码详解
def query_static_and_dynamic_values():"""查询静态字段和原始动态字段的值,验证交互效果"""print("\n=== 静态字段和动态字段值查询 ===")# 1. 只查询静态字段:动态字段被屏蔽,返回静态字段值(无则为 NULL)print("1. 只查询静态字段:")static_results = dynamic_client.query(collection_name="dynamic_demo",filter="",  # 无筛选条件output_fields=["id", "extra_info"],  # 仅查询静态字段(id 为静态主键,extra_info 为新增静态字段)limit=5)for result in static_results:# ID1 的 extra_info 静态字段为 NULL(原动态字段值需通过 $meta 查询)# ID2 的 extra_info 静态字段为 100(插入时指定的静态字段值)print(f" ID: {result['id']}, Static extra_info: {result.get('extra_info')}")# 2. 同时查询静态字段和原始动态值print("\n2. 同时查询静态和动态值:")combined_results = dynamic_client.query(collection_name="dynamic_demo",filter="",output_fields=["id","extra_info",  # 静态字段值"$meta['extra_info']",  # 原始动态字段值(通过 $meta 访问)"$meta['score']",  # 其他动态字段值"$meta['tags']"],limit=5)for result in combined_results:print(f" ID: {result['id']}")print(f" Static extra_info: {result.get('extra_info')}")  # 静态字段值# 动态字段值:key 为 "$meta[\"extra_info\"]"(字符串格式)print(f" Dynamic extra_info: {result.get('$meta[\"extra_info\"]')}")print(f" Dynamic score: {result.get('$meta[\"score\"]')}")print(f" Dynamic tags: {result.get('$meta[\"tags\"]')}")print()# 执行函数,查询并输出结果
query_static_and_dynamic_values()

四、注意事项总结

4.1 操作限制

  • 不可逆性:字段添加和属性更改操作通常不可撤销,需谨慎操作(如添加字段后无法删除,只能通过重建集合移除)。
  • 性能影响:向已加载到内存的集合添加字段,会增加内存占用(新字段需占用存储资源),可能短暂影响查询性能。
  • 数据类型约束:新字段必须设为可空,且不能添加向量字段、主键字段等受限类型。

4.2 可用性考虑

  • 短暂延迟:字段添加后,由于 Milvus 内部 Schema 同步,可能存在几秒到几十秒的延迟,期间查询可能无法获取新字段,需等待同步完成。
  • 查询兼容性:应用程序需处理新字段为 NULL 的情况(现有数据默认无值),避免空指针异常。
  • 默认值策略:添加带默认值的字段时,需确保默认值符合业务逻辑(如状态字段默认 "active"),避免数据不一致。

4.3 生产环境建议

  • 测试环境验证:所有字段操作(更改属性、添加字段)需先在测试环境验证,确认功能正常且无性能问题后,再在生产环境执行。
  • 备份策略:执行重要操作前,需通过 Milvus 的备份功能备份集合数据,防止操作失误导致数据丢失。
  • 监控告警:操作后需监控系统资源(内存、磁盘、CPU)使用情况,以及查询响应时间,及时处理异常。

http://www.dtcms.com/a/568814.html

相关文章:

  • ESP32C3开发指南(基于IDF):console控制台命令行交互功能
  • harmonyos的鸿蒙的跳转页面的部署参数传递
  • Git 简介和基础使用
  • HarmonyOS Marquee组件深度解析:构建高性能滚动视觉效果
  • 网站建设绿茶科技zencart 网站建设
  • vscode arm交叉编译 中 cmakeTools 编译器设置
  • 全自动化立体仓库巷道堆垛机使用西门子1500PLC通过EtherCAT主站转Profinet实现与EtherCAT协议的伺服进行通讯方案案例
  • MAC M1系统用pyinstaller分别打包支持ARM系统的app和支持Inter系统的APP
  • MTK平台详解`adb devices`输出的序列号组成
  • uniapp实现的Tab 选项卡组件模板
  • 学习Linux——网络基础管理
  • 杭州做网站比较出名的公司有哪些网站 内容建设存在的问题
  • C# ASP.NET MVC Model 分类:数据传输对象(DTO)—— 跨层传数的 “精简快递“
  • Elasticsearch 7.0 介绍与配置详解
  • 如何理解前端开发中框架一词及其优点?
  • ELK学习记录
  • Paho MQTT C 客户端源码深入解析
  • 零基础学AI大模型之RAG系统链路构建:文档切割转换全解析
  • Vue 核心语法详解:模板语法中的绑定表达式与过滤器(附 Vue3 替代方案)
  • CentOS7.6 部署 k3s 单机版
  • 【算法训练营 · 专项练习篇】Stream流与函数式编程
  • 泰州企业做网站百度地图怎么导航环线
  • int8_to_float(output_tensor->data.int8, output_float, load_class_num);
  • 使用Nmap扫描某个服务器所有开放端口
  • 如何看网站是用什么程序做的如何把qq音乐导入到wordpress
  • SpringCloud网关实战:路由与鉴权全解析
  • 基于ResNet50和PyTorch的猫狗图像分类系统设计与实现
  • 自回归模型例题(AR)与ACF/PACF图绘制
  • ESP32-WROOM-32E LED点灯系列
  • 《红色脉络:一部PLMN在中国的演进史诗 (1G-6G)》 第15篇 | 结语:无尽的前沿——PLMN的未来与中国的全球角色