メインコンテンツまでスキップ
バージョン: User Guides (BYOC)

Sparse Vector

疎ベクトル(Sparse vectors)は、情報検索や自然言語処理において、表面的な用語マッチングを捉えるための重要な手法です。密ベクトル(dense vectors)はセマンティックな理解に優れていますが、疎ベクトルは特に特殊な用語やテキスト識別子を検索する際に、より予測可能なマッチング結果を提供します。

概要

疎ベクトルは、高次元ベクトルの一種で、その大部分の要素がゼロであり、少数の次元のみが非ゼロ値を持つものです。下図に示すように、密ベクトルは通常、各位置に値を持つ連続した配列(例:[0.3, 0.8, 0.2, 0.3, 0.1])として表現されます。一方、疎ベクトルは非ゼロ要素とその次元インデックスのみを格納し、多くの場合 { index: value } のようなキー・バリュー形式(例:[{2: 0.2}, ..., {9997: 0.5}, {9999: 0.7}])で表現されます。

VPhswBhHmhJrh3byaVnc3onYnPc

トークン化とスコアリングにより、文書はボウ(bag-of-words)ベクトルとして表現できます。この場合、各次元は語彙内の特定の単語に対応し、文書内に存在する単語のみが非ゼロ値を持ち、疎ベクトル表現が生成されます。疎ベクトルは以下の2つのアプローチで生成できます:

  • 従来の統計手法TF-IDF(Term Frequency-Inverse Document Frequency)や BM25(Best Matching 25)など)は、コーパス全体における単語の出現頻度と重要度に基づいて重みを割り当てます。これらの手法は、各次元(トークンを表す)に対して単純な統計量をスコアとして計算します。Zilliz Cloud は BM25 方式による組み込みの 全文検索 機能を提供しており、テキストを自動的に疎ベクトルに変換するため、手動での前処理が不要です。このアプローチは、精度と完全一致が重要なキーワード検索に最適です。詳細については、Full Text Search を参照してください。

  • ニューラル疎埋め込みモデル は、大規模データセット上で学習された手法で、疎な表現を生成します。これらは通常、Transformer アーキテクチャを用いたディープラーニングモデルであり、セマンティックな文脈に基づいて用語を拡張および重み付けできます。Zilliz Cloud は、SPLADE のようなモデルによって外部で生成されたスパース埋め込みもサポートしています。詳細については、Embeddings を参照してください。

疎ベクトルと元のテキストは Zilliz Cloud に保存され、効率的な検索が可能です。以下の図は、全体のプロセスを示しています。

A7FvwnB5bhpBlKbgrzYcQijbnxg

📘Notes

疎ベクトルに加えて、Zilliz Cloud は密ベクトル(dense vectors)およびバイナリベクトル(binary vectors)もサポートしています。密ベクトルは深層的なセマンティック関係の把握に適しており、バイナリベクトルは類似度の高速比較やコンテンツの重複除去などのシナリオに優れています。詳細については、Dense Vector および Binary Vector を参照してください。

データ形式

以下のセクションでは、SPLADE のような学習済みの疎埋め込みモデルから得られるベクトルの保存方法を説明します。密ベクトルに基づくセマンティック検索を補完するものをお探しの場合は、シンプルさの点から SPLADE よりも BM25 を用いた Full Text Search を推奨します。品質評価を実施し、SPLADE の使用を決定した場合は、Embeddings を参照して、SPLADE による疎ベクトルの生成方法をご確認ください。

Zilliz Cloud は、以下の形式での疎ベクトル入力をサポートしています:

  • 辞書のリスト({dimension_index: value, ...} 形式)

    # Represent each sparse vector using a dictionary
    sparse_vectors = [{27: 0.5, 100: 0.3, 5369: 0.6} , {100: 0.1, 3: 0.8}]
  • スパース行列(scipy.sparse** クラスを使用)**

    from scipy.sparse import csr_matrix

    # First vector: indices [27, 100, 5369] with values [0.5, 0.3, 0.6]
    # Second vector: indices [3, 100] with values [0.8, 0.1]
    indices = [[27, 100, 5369], [3, 100]]
    values = [[0.5, 0.3, 0.6], [0.8, 0.1]]
    sparse_vectors = [csr_matrix((vals, ([0]*len(idx), idx)), shape=(1, 5369+1)) for idx, vals in zip(indices, values)]
  • タプルのイテラブルのリスト(例: [(dimension_index, value)]

    # Represent each sparse vector using a list of iterables (e.g. tuples)
    sparse_vector = [
    [(27, 0.5), (100, 0.3), (5369, 0.6)],
    [(100, 0.1), (3, 0.8)]
    ]

コレクションスキーマの定義

コレクションを作成する前に、フィールドを定義し、オプションでテキストフィールドを対応する疎ベクトル表現に変換する関数を指定するコレクションスキーマを定義する必要があります。

フィールドの追加

Zilliz Cloud クラスターで疎ベクトルを使用するには、以下のフィールドを含むスキーマでコレクションを作成する必要があります。

  • 疎ベクトルを格納するために予約された SPARSE_FLOAT_VECTOR フィールド。これは VARCHAR フィールドから自動生成されるか、または入力データ内で直接提供されます。

  • 通常、疎ベクトルが表す元のテキストもコレクション内に格納されます。元のテキストを格納するには VARCHAR フィールドを使用できます。

from pymilvus import MilvusClient, DataType

client = MilvusClient(uri="YOUR_CLUSTER_ENDPOINT")

schema = client.create_schema(
auto_id=True,
enable_dynamic_fields=True,
)

schema.add_field(field_name="pk", datatype=DataType.VARCHAR, is_primary=True, max_length=100)
schema.add_field(field_name="sparse_vector", datatype=DataType.SPARSE_FLOAT_VECTOR)
schema.add_field(field_name="text", datatype=DataType.VARCHAR, max_length=65535, enable_analyzer=True)

この例では、次の3つのフィールドが追加されています。

  • pk: このフィールドは主キーを格納し、VARCHAR データ型を使用します。最大長は100バイトで、自動生成されます。

  • sparse_vector: このフィールドは疎ベクトルを格納し、SPARSE_FLOAT_VECTOR データ型を使用します。

  • text: このフィールドはテキスト文字列を格納し、VARCHAR データ型を使用します。最大長は65535バイトです。

📘Notes

データ挿入時に指定されたテキストフィールドから または Zilliz Cloud が疎ベクトルの埋め込みを生成できるようにするには、関数を用いた追加の手順が必要です。詳細については、Full Text Search を参照してください。

Set Index Parameters

疎ベクトルに対するインデックス作成プロセスは、dense vectors の場合と似ていますが、指定するインデックスタイプ(index_type)、距離メトリクス(metric_type)、およびインデックスパラメータ(params)に違いがあります。

index_params = client.prepare_index_params()

index_params.add_index(
field_name="sparse_vector",
index_name="sparse_auto_index",
index_type="AUTOINDEX",
metric_type="IP"
)

この例では、SPARSE_INVERTED_INDEX インデックスタイプを IP メトリックとともに使用しています。詳細については、以下のリソースをご参照ください。

Create Collection

疎ベクトルおよびインデックスの設定が完了したら、疎ベクトルを含むコレクションを作成できます。以下の例では、create_collection メソッドを使用して my_collection という名前のコレクションを作成しています。

client.create_collection(
collection_name="my_collection",
schema=schema,
index_params=index_params
)

Insert data

コレクション作成時に定義されたすべてのフィールドに対してデータを提供する必要があります。ただし、自動生成されるフィールド(auto_id が有効になっている主キーなど)は除きます。組み込みのBM25関数を使用して疎ベクトルを自動生成している場合は、データ挿入時に疎ベクトルフィールドも省略する必要があります。

data = [
{
"text": "information retrieval is a field of study.",
"sparse_vector": {1: 0.5, 100: 0.3, 500: 0.8}
},
{
"text": "information retrieval focuses on finding relevant information in large datasets.",
"sparse_vector": {10: 0.1, 200: 0.7, 1000: 0.9}
}
]

client.insert(
collection_name="my_collection",
data=data
)

疎ベクトルを使用して類似性検索を実行するには、クエリデータと検索パラメータの両方を準備します。

# Prepare search parameters
search_params = {
"params": {"drop_ratio_search": 0.2}, # A tunable drop ratio parameter with a valid range between 0 and 1
}

# Query with sparse vector
query_data = [{1: 0.2, 50: 0.4, 1000: 0.7}]

次に、search メソッドを使用して類似性検索を実行します:

res = client.search(
collection_name="my_collection",
data=query_data,
limit=3,
output_fields=["pk"],
search_params=search_params,
consistency_level="Strong"
)

print(res)

# Output
# data: ["[{'id': '453718927992172266', 'distance': 0.6299999952316284, 'entity': {'pk': '453718927992172266'}}, {'id': '453718927992172265', 'distance': 0.10000000149011612, 'entity': {'pk': '453718927992172265'}}]"]

類似性検索パラメータの詳細については、基本的なベクトル検索を参照してください。