建立索引和查詢向量

選取說明文件版本:

本文說明如何使用儲存的嵌入生成索引及查詢嵌入。如要進一步瞭解如何儲存嵌入內容,請參閱「儲存向量嵌入內容」。

您可以使用 AlloyDB 建立 ScaNN、IVF、IVFFlat 和 HNSW 索引。

事前準備

開始建立索引前,請先完成下列前置條件。

  • 嵌入向量會新增至 AlloyDB 資料庫中的資料表。

  • 已安裝 vector 擴充功能 0.5.0 以上版本,該版本以 pgvector 為基礎,由 Google 針對 AlloyDB 擴充。

    CREATE EXTENSION IF NOT EXISTS vector;
    
  • 如要生成 ScaNN 索引,除了 vector 擴充功能外,還須安裝 alloydb_scann 擴充功能。

    CREATE EXTENSION IF NOT EXISTS alloydb_scann;
    

建立索引

您可以為資料庫中的資料表建立下列任一索引類型。

建立 ScaNN 索引

AlloyDB alloydb_scann 是 Google 開發的 PostgreSQL 擴充功能,採用ScaNN 演算法,可實作高效率的最近鄰索引。

ScaNN 索引是樹狀結構的量化索引,用於近似最鄰近搜尋。與 HNSW 相比,這項演算法的索引建構時間較短,記憶體用量也較少。此外,相較於 HNSW,這項服務可根據工作負載提供更快的 QPS。

兩層樹狀結構 ScaNN 索引

如要使用 ScaNN 演算法,將兩層樹狀結構索引套用至含有已儲存向量嵌入的資料欄,請執行下列 DDL 查詢:

CREATE INDEX INDEX_NAME ON TABLE
  USING scann (EMBEDDING_COLUMN DISTANCE_FUNCTION)
  WITH (num_leaves=NUM_LEAVES_VALUE);

更改下列內容:

  • INDEX_NAME:要建立的索引名稱,例如 my-scann-index。索引名稱會在資料庫中共用。請確保資料庫中每個表格的索引名稱皆不重複。

  • TABLE:要新增索引的資料表。

  • EMBEDDING_COLUMN:儲存vector資料的資料欄。

  • DISTANCE_FUNCTION:要搭配這個索引使用的距離函式。選擇下列其中一個選項:

    • L2 距離: l2

    • 點積: dot_product

    • 餘弦距離: cosine

  • NUM_LEAVES_VALUE:要套用至這個索引的分區數量。可設為 1 到 1048576 之間的任何值。如要進一步瞭解如何決定這個值,請參閱「調整 ScaNN 索引」。

三層樹狀結構 ScaNN 索引

如要使用 ScaNN 演算法,為含有儲存向量嵌入的資料欄建立三層樹狀結構索引,請執行下列 DDL 查詢:

CREATE INDEX INDEX_NAME ON TABLE
  USING scann (EMBEDDING_COLUMN DISTANCE_FUNCTION)
  WITH (num_leaves=NUM_LEAVES_VALUE, max_num_levels = MAX_NUM_LEVELS);

更改下列內容:

  • MAX_NUM_LEVELS:k-means 分群樹狀結構的層級數量上限。設為 1(預設值) 可進行兩層樹狀結構量化,設為 2 則可進行三層樹狀結構量化。

建立索引後,您可以按照「使用指定文字執行最鄰近查詢」中的操作說明,執行使用該索引的最鄰近搜尋查詢。

設定索引參數時,必須在 QPS 和喚回度之間取得適當平衡。如要進一步瞭解如何調整 ScaNN 索引,請參閱「調整 ScaNN 索引」。

如要在使用 real[] 資料類型 (而非 vector) 的嵌入資料欄上建立這個索引,請將該資料欄轉換為 vector 資料類型:

CREATE INDEX INDEX_NAME ON TABLE
  USING scann (CAST(EMBEDDING_COLUMN AS vector(DIMENSIONS)) DISTANCE_FUNCTION)
  WITH (num_leaves=NUM_LEAVES_VALUE, max_num_levels = MAX_NUM_LEVELS);

將 DIMENSIONS 替換為嵌入資料欄的維度寬度。如要進一步瞭解如何尋找維度,請參閱「向量函式」中的 vector_dims 函式。

如要查看索引進度,請使用 pg_stat_progress_create_index 檢視畫面:

SELECT * FROM pg_stat_progress_create_index;

「phase」欄會顯示索引建立作業目前的狀態,而「building index: tree training」階段會在索引建立後消失。

如要調整索引,在目標喚回度和 QPS 之間取得平衡,請參閱「調整 ScaNN 索引」。

分析已建立索引的資料表

建立 ScaNN 索引後,您必須執行 ANALYZE 指令,更新資料統計資料。

ANALYZE TABLE;

執行查詢

在資料庫中儲存嵌入並建立索引後,即可使用 pgvector 查詢功能開始查詢。您無法使用 alloydb_scann 擴充功能執行大量搜尋查詢。

如要找出嵌入向量最鄰近的語意鄰居,可以執行下列查詢範例,並設定與建立索引時相同的距離函式。

  SELECT * FROM TABLE
    ORDER BY EMBEDDING_COLUMN DISTANCE_FUNCTION_QUERY ['EMBEDDING']
    LIMIT ROW_COUNT

更改下列內容:

  • TABLE:包含要與文字比較之嵌入內容的資料表。

  • INDEX_NAME:要使用的索引名稱,例如 my-scann-index。

  • EMBEDDING_COLUMN:包含儲存嵌入的資料欄。

  • DISTANCE_FUNCTION_QUERY:要用於這項查詢的距離函式。根據建立索引時使用的距離函式,選擇下列其中一項:

    • L2 距離: <->

    • 內積: <#>

    • 餘弦距離: <=>

  • EMBEDDING:要找出最鄰近儲存語意鄰居的嵌入向量。

  • ROW_COUNT:要傳回的列數。

    如果只要單一最佳相符項目,請指定 1。

如要查看其他查詢範例,請參閱「查詢」。

您也可以使用 embedding() 函式,將文字轉譯為向量。您將向量套用至其中一個 pgvector 最鄰近運算子 (<-> 代表 L2 距離),找出語意最相似嵌入的資料庫資料列。

由於 embedding() 會傳回 real 陣列,因此您必須明確將 embedding() 呼叫轉換為 vector,才能搭配 pgvector 運算子使用這些值。

  CREATE EXTENSION IF NOT EXISTS google_ml_integration;
  CREATE EXTENSION IF NOT EXISTS vector;

  SELECT * FROM TABLE
    ORDER BY EMBEDDING_COLUMN::vector
    <-> embedding('MODEL_IDVERSION_TAG', 'TEXT')
    LIMIT ROW_COUNT

更改下列內容:

  • MODEL_ID:要查詢的模型 ID。

    如果使用 Vertex AI Model Garden,請指定 text-embedding-005 做為模型 ID。這些是 AlloyDB 可用於文字嵌入的雲端式模型。詳情請參閱「文字嵌入」。

  • 選用:VERSION_TAG:要查詢的模型版本標記。在標記開頭加上 @。

    如果您使用 Vertex AI 搭配 text-embedding 英文模型,請指定其中一個版本標記,例如text-embedding-005,如「模型版本」一節所列。

    Google 強烈建議您一律指定版本標記。如未指定版本標記,AlloyDB 一律會使用最新模型版本,這可能會導致非預期結果。

  • TEXT:要翻譯成向量嵌入的文字。

後續步驟