Индексирование полей StructArray
Создайте индексы для подполей StructArray перед выполнением векторного поиска или ускорением скалярной фильтрации. Для поля StructArray целевым объектом индекса является путь к подполю, например chunks[emb_list_vector], chunks[emb] или chunks[section].
На этой странице используется коллекция tech_articles из раздела «Создание поля StructArray». Поле StructArray chunks содержит скалярные подполя для фильтрации и векторные подполя для поиска.
Перед началом работы
Убедитесь, что схема коллекции уже содержит поле StructArray « chunks » и что в неё вставлены данные.
| Путь к подполю | Тип | Назначение индекса |
|---|---|---|
chunks[emb_list_vector] | FLOAT_VECTOR | Поиск в EmbeddingList с использованием метрик MAX_SIM*. |
chunks[emb] | FLOAT_VECTOR | Поиск на уровне элементов с использованием обычных векторных метрик. |
chunks[section] | VARCHAR | Категориальная фильтрация. |
chunks[quality_score] | FLOAT | Числовая фильтрация и предикаты диапазонного типа. |
chunks[has_code] | BOOL | Булева фильтрация. |
Векторное поле или векторное подполе допускает только один индекс. Если вам нужен как поиск по EmbeddingList, так и поиск на уровне элементов, создайте два отдельных векторных подполя и проиндексируйте их по отдельности. На этой странице поле « chunks[emb_list_vector] » проиндексировано для поиска по EmbeddingList, а поле « chunks[emb] » — для поиска на уровне элементов.
Выбор индексов
Используйте режим поиска, чтобы выбрать семейство векторных метрик.
| Цель поиска или фильтрации | Целевой путь | Что выбрать |
|---|---|---|
| Поиск в EmbeddingList | chunks[emb_list_vector] | Семейство метрик « MAX_SIM* ». |
| Векторный поиск на уровне элементов | chunks[emb] | Обычное семейство векторных метрик, например COSINE, IP или L2. |
| Фильтрация по строке или категории | chunks[section] | Скалярный индекс, поддерживаемый вашей целевой системой. |
| Фильтрация по числовому диапазону | chunks[quality_score], chunks[page] | скалярный индекс, поддерживаемый вашей целью. |
| Фильтрация по булевому значению | chunks[has_code] | Скалярный индекс, поддерживаемый вашей целевой платформой. |
Поиск по EmbeddingList рассматривает векторы в подполе вектора StructArray как список вложений и возвращает результаты на уровне сущностей. Поиск на уровне элементов выполняет поиск по каждому элементу Struct независимо и может возвращать смещение найденного элемента.
Создание векторных индексов
В следующем примере создаются два векторных индекса. Первый индекс использует метрику « MAX_SIM* » для поиска по списку вложений. Второй индекс использует обычную векторную метрику для поиска на уровне элементов.
from pymilvus import MilvusClient
client = MilvusClient(
uri="http://localhost:19530",
token="root:Milvus",
)
index_params = client.prepare_index_params()
# Index for EmbeddingList search.
index_params.add_index(
field_name="chunks[emb_list_vector]",
index_name="chunks_emb_list_max_sim",
index_type="HNSW",
metric_type="MAX_SIM_COSINE",
params={
"M": 16,
"efConstruction": 200,
},
)
# Index for element-level search.
index_params.add_index(
field_name="chunks[emb]",
index_name="chunks_emb_cosine",
index_type="HNSW",
metric_type="COSINE",
params={
"M": 16,
"efConstruction": 200,
},
)
client.create_index(
collection_name="tech_articles",
index_params=index_params,
)
Предупреждение
Не создавайте индекс с метрикой « MAX_SIM* » и индекс с обычной векторной метрикой для одного и того же подполя вектора. Если требуются оба режима поиска, запишите векторы в два отдельных подполя вектора и создайте по одному индексу для каждого подполя.
Создание скалярных индексов
Создавайте скалярные индексы на скалярных подполях StructArray, если вы используете их в фильтрах. Используйте тот же синтаксис пути, что и для structArray[subfield].
index_params = client.prepare_index_params()
index_params.add_index(
field_name="chunks[section]",
index_name="chunks_section_inverted",
index_type="INVERTED",
)
index_params.add_index(
field_name="chunks[has_code]",
index_name="chunks_has_code_inverted",
index_type="INVERTED",
)
index_params.add_index(
field_name="chunks[quality_score]",
index_name="chunks_quality_score_sort",
index_type="STL_SORT",
)
index_params.add_index(
field_name="chunks[page]",
index_name="chunks_page_sort",
index_type="STL_SORT",
)
client.create_index(
collection_name="tech_articles",
index_params=index_params,
)
Скалярные индексы не являются обязательными, но полезны, если скалярные подполя StructArray часто встречаются в фильтрах, таких как element_filter(chunks, $[quality_score] > 0.9) или MATCH_ANY(chunks, $[section] == "index").
Совместимость метрик индексов
Используйте приведенные ниже таблицы для выбора типа индекса и типа метрики для векторного подполя StructArray. Начните с конечной цели, а затем выберите семейство метрик в зависимости от режима поиска.
Выберите тип индекса и тип метрики Milvus из приведенных ниже таблиц совместимости.
Поиск по EmbeddingList
Поиск по EmbeddingList использует метрики типа MAX_SIM*. Он рассматривает векторы в подполе векторного типа StructArray как список вложений и возвращает результаты на уровне сущностей.
| Тип данных подполя вектора | Тип индекса | Тип метрики |
|---|---|---|
FLOAT_VECTOR, FLOAT16_VECTOR, BFLOAT16_VECTOR | IVF_FLAT, IVF_FLAT_CC, HNSW, HNSW_SQ, HNSW_PQ, HNSW_PRQ, DISKANN | MAX_SIM, MAX_SIM_COSINE, MAX_SIM_IP, MAX_SIM_L2 |
INT8_VECTOR | HNSW, HNSW_SQ, HNSW_PQ, HNSW_PRQ | MAX_SIM, MAX_SIM_COSINE, MAX_SIM_IP, MAX_SIM_L2 |
BINARY_VECTOR | HNSW | MAX_SIM_HAMMING, MAX_SIM_JACCARD |
Поиск на уровне элементов
Поиск на уровне элементов использует стандартные векторные метрики. Он выполняет поиск по каждому элементу структуры независимо и может возвращать смещение найденного элемента.
| Тип данных векторного подполя | Тип индекса | Тип метрики |
|---|---|---|
FLOAT_VECTOR, FLOAT16_VECTOR, BFLOAT16_VECTOR | FLAT, IVF_FLAT, IVF_FLAT_CC, IVF_SQ8, IVF_SQ_CC, IVF_PQ, SCANN, IVF_RABITQ, IVF_RABITQ_FASTSCAN, HNSW, HNSW_SQ, HNSW_PQ, HNSW_PRQ, DISKANN | L2, IP, COSINE |
INT8_VECTOR | HNSW, HNSW_SQ, HNSW_PQ, HNSW_PRQ | L2, IP, COSINE |
BINARY_VECTOR | HNSW | HAMMING, JACCARD |
BINARY_VECTOR | BIN_FLAT | HAMMING, JACCARD, SUBSTRUCTURE, SUPERSTRUCTURE, MHJACCARD |
BINARY_VECTOR | BIN_IVF_FLAT | HAMMING, JACCARD |
Информацию о поддержке конкретных версий и других ограничениях см. в разделе «Ограничения StructArray».
Проверка индексов
После создания индексов опишите индексы коллекции или списка, чтобы убедиться, что ожидаемые пути к подполям проиндексированы.
indexes = client.list_indexes(
collection_name="tech_articles",
)
print(indexes)
Вы также можете описать конкретный индекс, если ваша версия SDK предоставляет API для описания индексов.
index = client.describe_index(
collection_name="tech_articles",
index_name="chunks_emb_cosine",
)
print(index)
Правила индексирования
| Правило | Пояснение |
|---|---|
| Используйте синтаксис путей для индексов подполей. | Индексируйте chunks[emb], а не emb или chunks.emb. |
| Одно векторное подполе допускает один индекс. | Используйте отдельные векторные подполя, если вам нужны разные семейства метрик. |
Для поиска по EmbeddingList используйте метрику MAX_SIM*. | Для запросов по EmbeddingList требуется индекс, построенный с использованием метрики MAX_SIM*. |
| Для поиска на уровне элементов используйте обычные векторные метрики. | При поиске на уровне элементов используются данные запросов обычных векторных метрик, таких как COSINE, IP или L2. |
| Индексируйте скалярные подполя, которые появляются в фильтрах. | Используйте типы скалярных индексов, поддерживаемые вашей целевой платформой. |
| Учитывайте ограничения на векторные поля. | Общее количество векторных полей и векторных подполей ограничено. Перед добавлением большого количества векторных подполей ознакомьтесь с разделом «Ограничения StructArray». |
Распространенные ошибки
Создание индекса на поле типа «
chunks.emb» вместо «chunks[emb]».Создание только индекса
MAX_SIM*, а затем попытка запустить поиск на уровне элементов в том же подполе.Создание только обычного векторного индекса, а затем попытка выполнить поиск по EmbeddingList в том же подполе.
Повторное использование одного векторного подполя как для метрики
MAX_SIM*, так и для обычной векторной метрики.Отсутствие скалярных индексов для часто используемых фильтров StructArray.
Индексирование подполя StructArray, которое отсутствует в схеме Struct.
Следующие шаги
Чтобы выполнить поиск EmbeddingList на уровне сущностей или векторный поиск на уровне элементов, ознакомьтесь с разделом «Базовый векторный поиск с использованием StructArray».
Чтобы фильтровать скалярные подполя StructArray во время поиска, ознакомьтесь со статьей «Фильтрованный поиск с использованием StructArray».
Чтобы ознакомиться с ограничениями на индексы и метрики, ознакомьтесь со статьей «Ограничения StructArray».