將資料插入 StructArray 欄位
當每個實體包含一個有序的結構化元素清單時,請將資料插入 StructArray 欄位中。在插入載荷中,StructArray 欄位以物件陣列的形式呈現。每個物件代表一個 Struct 元素,並使用集合架構中定義的 Struct 子欄位名稱。
本頁使用《建立 StructArray 欄位》中的tech_articles 集合。每個實體皆為一篇技術文章,而chunks 欄位則將文章片段儲存為 Struct 元素。
開始之前
請確認集合架構中已包含chunks StructArray欄位。
| 欄位 | 類型 | 插入值 |
|---|---|---|
doc_id | INT64 | 文章 ID。 |
title | VARCHAR | 文章標題。 |
category | VARCHAR | 文章類別。 |
title_vector | FLOAT_VECTOR | 文章層級嵌入。 |
chunks | ARRAY | 一段落物件清單。 |
chunks 中的每個物件都必須遵循 Struct 結構。
| 子欄位 | 類型 | 插入值 |
|---|---|---|
text | VARCHAR | 區塊文字。 |
section | VARCHAR | 區段名稱,例如index 、search 或filter 。 |
page | INT64 | 頁碼或邏輯位置。 |
quality_score | FLOAT | 區塊層級的評分。 |
has_code | BOOL | 該區塊是否包含程式碼。 |
emb_list_vector | FLOAT_VECTOR | 為 EmbeddingList 搜尋所編寫的向量。 |
emb | FLOAT_VECTOR | 為元素層級搜尋所撰寫的向量。 |
在插入式有效載荷中,chunks 是一個常規欄位,其值為 Struct 物件的陣列。在每個物件內部,請使用text 和emb 等子欄位名稱。僅在插入完成後,當您建立索引、執行搜尋、建立篩選器或指定輸出欄位時,才使用路徑語法,例如chunks[text] 或chunks[emb] 。
了解插入資料的結構
chunks 的值是一個由 Struct 元素組成的陣列。每個元素皆為一個物件,其鍵為子欄位名稱。
{
"doc_id": 1,
"title": "StructArray indexing patterns",
"category": "index",
"title_vector": [0.12, 0.08, 0.32, 0.48],
"chunks": [
{
"text": "Create one index for each vector subfield.",
"section": "index",
"page": 1,
"quality_score": 0.96,
"has_code": false,
"emb_list_vector": [0.10, 0.20, 0.30, 0.40],
"emb": [0.10, 0.20, 0.30, 0.40]
},
{
"text": "Use MAX_SIM metrics for EmbeddingList search.",
"section": "index",
"page": 2,
"quality_score": 0.91,
"has_code": true,
"emb_list_vector": [0.16, 0.24, 0.35, 0.45],
"emb": [0.16, 0.24, 0.35, 0.45]
}
]
}
emb_list_vector 和emb 是獨立的向量子欄位,因為它們支援不同的搜尋模式。EmbeddingList 搜尋會將 StructArray 欄位中的所有向量視為一個嵌入清單,並返回包含MAX_SIM* 指標的實體層級結果。元素層級搜尋則會獨立搜尋每個 Struct 元素,並可返回匹配元素的偏移量。為簡化說明,此範例在兩個欄位中儲存相同的向量值。 在生產環境的應用程式中,當兩種搜尋模式使用相同的區塊嵌入時,可將相同的嵌入向量儲存於兩個子欄位中;若兩種搜尋模式使用不同的表示法,則可儲存不同的嵌入向量。
插入資料列
請使用 `client.insert() ` 來插入包含 StructArray 值的資料列。
from pymilvus import MilvusClient
client = MilvusClient(
uri="http://localhost:19530",
token="root:Milvus",
)
data = [
{
"doc_id": 1,
"title": "StructArray indexing patterns",
"category": "index",
"title_vector": [0.12, 0.08, 0.32, 0.48],
"chunks": [
{
"text": "Create one index for each vector subfield.",
"section": "index",
"page": 1,
"quality_score": 0.96,
"has_code": False,
"emb_list_vector": [0.10, 0.20, 0.30, 0.40],
"emb": [0.10, 0.20, 0.30, 0.40],
},
{
"text": "Use MAX_SIM metrics for EmbeddingList search.",
"section": "index",
"page": 2,
"quality_score": 0.91,
"has_code": True,
"emb_list_vector": [0.16, 0.24, 0.35, 0.45],
"emb": [0.16, 0.24, 0.35, 0.45],
},
],
},
{
"doc_id": 2,
"title": "Filtered StructArray search",
"category": "filter",
"title_vector": [0.20, 0.18, 0.22, 0.40],
"chunks": [
{
"text": "Use element_filter to match scalar conditions within the same Struct element.",
"section": "filter",
"page": 1,
"quality_score": 0.93,
"has_code": True,
"emb_list_vector": [0.21, 0.18, 0.33, 0.44],
"emb": [0.21, 0.18, 0.33, 0.44],
},
{
"text": "MATCH_LEAST checks how many elements satisfy a predicate.",
"section": "filter",
"page": 2,
"quality_score": 0.88,
"has_code": False,
"emb_list_vector": [0.24, 0.22, 0.31, 0.39],
"emb": [0.24, 0.22, 0.31, 0.39],
},
],
},
{
"doc_id": 3,
"title": "Element-level search with offsets",
"category": "search",
"title_vector": [0.33, 0.11, 0.29, 0.37],
"chunks": [
{
"text": "Element-level search can return the offset of the matched Struct element.",
"section": "search",
"page": 1,
"quality_score": 0.95,
"has_code": False,
"emb_list_vector": [0.32, 0.14, 0.28, 0.41],
"emb": [0.32, 0.14, 0.28, 0.41],
}
],
},
]
result = client.insert(
collection_name="tech_articles",
data=data,
)
print(result)
插入可為空的 StructArray 欄位
若 `chunks ` 欄位為可為空類型,實體可將整個 `chunks ` 欄位設為 null。在 Python 中,請使用 `None ` 來表示 null 值。
client.insert(
collection_name="tech_articles",
data=[
{
"doc_id": 10,
"title": "Article without chunks yet",
"category": "draft",
"title_vector": [0.05, 0.10, 0.15, 0.20],
"chunks": None,
}
],
)
當可為空的 StructArray 欄位包含有效的 StructArray 值時,該值中的所有子欄位應皆為 null 或具有有效值。若插入的實體中,部分子欄位設定為 null 而其他子欄位設定為有效值,將會導致錯誤。
警告
可為空的 StructArray 欄位僅在 Milvus v3.0.x 中提供。若您要動態將 StructArray 欄位新增至現有集合中,新增的欄位必須為可為空,且現有實體針對該新欄位的所有子欄位均會傳回 `null `。
驗證插入的資料
您可以查詢集合並返回 StructArray 欄位或選定的子欄位。
rows = client.query(
collection_name="tech_articles",
filter="doc_id in [1, 2, 3]",
output_fields=[
"doc_id",
"title",
"chunks[text]",
"chunks[section]",
"chunks[quality_score]",
],
)
for row in rows:
print(row)
僅在查詢、搜尋、篩選或建立索引時,才應使用 StructArray 欄位路徑(例如chunks[text] )。插入資料時,仍應使用位於chunks 下的嵌套物件。
插入規則
| 規則 | 說明 |
|---|---|
| 請對 StructArray 欄位使用物件陣列。 | chunks 的值是一個清單,而清單中的每個項目皆為一個 Struct 元素。 |
| 在每個 Struct 元素內使用子欄位名稱。 | 請將 `{"text": "...", "emb": [...]} ` 插入 `chunks` 中,而非 `{"chunks[text]": "..."}`。 |
| 請符合 Struct 架構規範。 | 每個 Struct 元素必須使用 Struct 模式中定義的子欄位。 |
| 向量維數必須與結構體模式相符。 | 向量值必須與其向量子欄位所設定的dim 相符。 |
須遵守max_capacity 。 | 單一實體中的 Struct 元素數量不得超過 StructArray 欄位的max_capacity 。 |
| 針對不同的搜尋模式,請使用獨立的向量子欄位。 | 如果同時需要 EmbeddingList 搜尋和元素層級搜尋,請將向量值寫入兩個向量子欄位中。 |
僅當欄位可為空時,才使用null 。 | 不可為空的 StructArray 欄位需要有效的 StructArray 值。 |
常見錯誤
在插入有效載荷中使用如 `
chunks[text]` 這樣的欄位路徑。從 Struct 元素中省略必填子欄位。
插入維數錯誤的向量。
插入的 Struct 元素數量超過
max_capacity所允許的數量。僅將一個子欄位設定為
null,而同一 StructArray 值中的其他子欄位卻是有效的。僅將向量寫入 `
emb_list_vector`,隨後卻嘗試在 `chunks[emb]` 上執行元素層級搜尋。僅將向量寫入 `
emb`,隨後嘗試在 `chunks[emb_list_vector]` 上執行 `EmbeddingList` 搜尋。
後續步驟
若要為
chunks[emb_list_vector]、chunks[emb]及標量子欄位建立索引,請參閱《索引 StructArray 欄位》。若要搜尋 StructArray 向量子欄位,請參閱《使用 StructArray 進行基本向量搜尋》。
若要檢視可為空的行為及特定版本的限制,請參閱《StructArray 限制》。