使用MariaDB进行向量存储、索引和搜索

當您開發生成式 AI 應用時,通常會在您的基礎設施中引入三個額外的組件:嵌入器、一個大型語言模型 (LLM) 和一個向量數據庫。

然而,如果您使用的是 MariaDB,您不需要引入一個額外的數據庫及其自己的 SQL 方言——更糟的是——其自己的專有 API。自 MariaDB 版本 11.7(以及 MariaDB Enterprise Server 11.4)起,您可以簡單地將您的嵌入(或向量)存儲在任何表的任何列中——無需讓您的應用程序成為數據庫的多語言者。

“在 宣佈 MariaDB Server 的向量搜索預覽後,向量搜索功能現在已被添加到 MariaDB Community Server 11.7 版本中,” 寫道 Ralf Gebhardt,MariaDB 的 MariaDB Server 產品經理。這包括一種新的數據類型 (VECTOR)、向量索引和一組用於向量操作的函數。

為什麼生成式 AI 應用需要向量?

向量在生成式人工智慧應用中是必要的,因為它們將複雜的涵義嵌入到一個緊湊的固定長度數組(向量)中。這在檢索增強生成(或RAG)的情境中更為明確。這個技術允許您從來源(API、文件、數據庫)中檢索相關數據,以增強 AI 模型的輸入,通常這些數據是專有的商業數據。

由於您的數據來源可能非常廣泛,您需要找到相關片段的方法,因為當前的 AI 模型具有有限的上下文窗口 — 您不能簡單地將所有數據添加到提示中。通過創建數據塊並運行這些數據塊通過一個名為嵌入器的特殊 AI 模型,您可以生成向量,並使用接近搜索技術來找到相關信息以附加到提示中。

例如,接受用戶在推薦對話機器人中的以下輸入:

Plain Text

 

由於您的 AI 模型未經過訓練,不包含在線商店中產品信息的確切數據,您需要在將提示發送到模型之前檢索最相關的產品及其信息。

為此,您將用戶的原始輸入發送給一個嵌入器,並獲得一個向量,稍後您可以使用該向量獲取與用戶輸入最接近的,比如說,10個產品。一旦獲取了這些信息(稍後我們將看到如何在 MariaDB 中實現此操作),您可以將增強的提示發送到您的 AI 模型:

Plain Text

 

這將導致使用您自己數據的 AI 預測。

為向量存儲創建表格

要在MariaDB中存儲向量,請使用新的VECTOR數據類型。例如:

MariaDB SQL

 

CREATE TABLE products (
    id INT PRIMARY KEY,
    name VARCHAR(100),
    description TEXT,
    embedding VECTOR(2048)
);

在這個例子中,embedding列可以容納2048維的向量。您必須匹配您的嵌入器生成的維數。

創建向量索引

為了提高讀取性能,將索引添加到您的向量列非常重要。這加快了相似性搜索的速度。您可以在表創建時定義索引,如下所示:

MariaDB SQL

 

CREATE TABLE products (
    id INT PRIMARY KEY,
    name VARCHAR(100),
    description TEXT,
    embedding VECTOR(2048) NOT NULL,
    VECTOR INDEX (embedding)
);

為了更好地控制,您可以指定數據庫服務器將用於構建索引的距離函數,以及MariaDB使用的M of the 層次導航小世界(HNSW)算法。例如:

MariaDB SQL

 

CREATE TABLE products (
    id INT PRIMARY KEY,
    name VARCHAR(100),
    description TEXT,
    embedding VECTOR(2048) NOT NULL,
    VECTOR INDEX (embedding) M=8 DISTANCE=cosine
);

查看文檔以獲取有關這些配置的更多信息。

插入向量

當您通過嵌入器傳遞數據(文本、圖像、音頻)時,您會得到一個向量。通常,這是一個以JSON格式為數組的一系列數字。要將此向量插入MariaDB表中,您可以使用VEC_FromText函數。例如:

MariaDB SQL

 

INSERT INTO products (name, embedding)
VALUES
  ("Alarm clock", VEC_FromText("[0.001, 0, ...]")),
  ("Cow figure", VEC_FromText("[1.0, 0.05, ...]")),
  ("Bicycle", VEC_FromText("[0.2, 0.156, ...]"));

請記住,插入的向量必須具有在CREATE TABLE語句中定義的正確維數。

相似性搜索(比較向量)

在RAG應用中,您將用戶輸入發送到嵌入器以獲取向量。然後,您可以查詢數據庫中與該向量更接近的記錄。更接近的向量表示語義上相似的數據。在撰寫本文時,MariaDB有兩個距離函數可用於相似性或接近性搜索:

  • VEC_DISTANCE_EUCLIDEAN:計算兩個向量之間的直線距離。最適合用於來自原始、未標準化數據的向量或空間分離與相似性直接相關的場景,例如比較位置或數值特徵。然而,對於高維或標準化的嵌入,它的效果較差,因為它對向量大小的差異敏感。
  • VEC_DISTANCE_COSINE:測量向量之間的角度差異。適合比較標準化的嵌入,特別是在語義應用中,如文本或文檔檢索。它在捕捉意義或上下文的相似性方面表現出色。

請記住,使用之前的函數進行的相似性搜索僅為近似,並且高度依賴於計算向量的質量,因此也依賴於所使用的嵌入器的質量。

以下示例將查找與給定向量最相似的前10個產品($user_input_vector應替換為嵌入器根據用戶輸入返回的實際向量):

MariaDB SQL

 

SELECT id, name, description
FROM products
ORDER BY VEC_DISTANCE_COSINE(
  VEC_FromText($user_input_vector),
  embedding
)
LIMIT 10;

VEC_DISTANCE_COSINEVEC_DISTANCE_EUCLIDEAN 函數接受兩個向量。在之前的範例中,其中一個向量是根據用戶輸入計算出的向量,另一個則是 products 表中每條記錄的對應向量。

實用範例

我準備了一個使用 Java 並且沒有 AI 框架的實用範例,讓您真正了解利用 MariaDB 的向量搜索功能創建生成性 AI 應用程序的過程。您可以在 GitHub 上找到代碼。

Source:
https://dzone.com/articles/vector-storage-indexing-and-search-with-mariadb