23
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

RetailAI AdventurersAdvent Calendar 2023

Day 25

【埋め込みベクトルDB】ベッチ数の変化を知りたいんじゃ!

Last updated at Posted at 2023-12-24

はじめに

RetailAI Advent Calendar 2023 の 25日目の記事です!

みなさん、メリークリスマス。聖しこの夜にはベッチ数を知りたいですよね。というわけで、今日はベッチ数の変化を調べてみようと思います。

生成AIの飛躍的な進歩によって、ベクトルデータベースも脚光を浴びている昨今、破局的忘却(catastrophic forgetting)によって、前回ちょっと書かせてもらったpromptbaseなどを駆使して、せっかく組み立てたCoTの再現性が失われたりしては、昔ドラクエ3で冒険の書が消えちゃうのよりショックが大きいです。

そこで、いろんな方法でベクトルデータベースの評価や検証を行っていきたいのですが、そのうちの一つとして、TDA(トポロジカルデータ分析)という手法を使って、ベッチ数を数えたいーというモチベーションです。

↓早い話、黒丸の数が知りたいのです。

image.png

目次

  1. ベッチ数とは
  2. ベッチ数を数えよう
  3. まとめ
  4. 参考文献

ベッチ数とは

ベッチ数とは、堅苦しく言えばトポロジーを考える際に、位相空間の構造を数値的に表すための不変量です。これによって、位相空間の連結成分の数、輪の数、空洞の数など、位相空間の基本的な特徴を表すことができます。

b_k(X) = \text{dim}(H_k(X, \mathbb{Z}))

↑この式で、

X は位相空間
H
k

(X,Z) は、位相空間 X の k 次ホモロジー群
Z は整数環

ベッチ数は、位相空間の次元によっても異なります。例えば、1 次元の位相空間の場合、ベッチ数は 0 または 1 のどちらかになります。2 次元の位相空間の場合、ベッチ数は 0、1、または 2 のいずれかになります。

例えば、トーラスのベッチ数は 1、1 です。これは、トーラスが 1 つの連結成分と 1 つの輪を持つことを意味します。
また、球のベッチ数は 0、0 です。これは、球が連結成分と輪を持たないことを意味します。
円柱のベッチ数は 1、1 です。これは、円柱が 1 つの連結成分と 1 つの輪を持つことを意味します。

うんぬんかんぬん・・・

と、まあ要するに、ベッチ数は、位相空間の基本的な特徴を表すことができて便利です。ですので、今回は、大規模言語の埋め込みベクトルデータベースの世代毎にベッチ数を数えて、情報分布に変化が生じてないか調べたい、そういうモチベーションになります。

#ベッチ数を数えよう

まずは、適当な埋め込みベクトルデータベースを生成してみます。これは、どんな言語モデルでも構いません。


import numpy as np
import matplotlib.pyplot as plt
import scipy.spatial.distance as ssd

# モデルをロードする
model = load_model("model.h5")

# テキストデータのリスト
texts_1 = ["これはサンプルデータ1です。", "これはサンプルデータ2です。", "これはサンプルデータ3です。"]
texts_2 = ["これはサンプルデータ4です。", "これはサンプルデータ5です。", "これはサンプルデータ6です。"]

# テキストデータのベクトル化
vectors_1 = []
for text in texts_1:
    vectors_1.append(model.predict(tf.convert_to_tensor(text)))
vectors_2 = []
for text in texts_2:
    vectors_2.append(model.predict(tf.convert_to_tensor(text)))

vectors_1 = vectors_1.reshape(-1, 2)
vectors_2 = vectors_2.reshape(-1, 2)

単純な例ですが、ベッチ数を数えるには十分です。それでは、実際に数えてみましょう。


betti_numbers_1 = []
for vector in vectors_1:
    betti_numbers_1.append(np.linalg.matrix_rank(vector))
betti_numbers_2 = []
for vector in vectors_2:
    betti_numbers_2.append(np.linalg.matrix_rank(vector))

# ベッチ数の比較
print("ベッチ数1:", betti_numbers_1)
print("ベッチ数2:", betti_numbers_2)

こちらの実行結果は、以下のようになります。

ベッチ数1: [1 2]
ベッチ数2: [1 2]

この結果から、世代1と世代2のベッチ数に違いがないことがわかります。つまり、埋め込みベクトルデータベースの性能は、世代によって変化していないことが示唆されます。

あるいは、TDAパッケージを用いると更に色々なことが分かります。scikit-tda をインストールしてみましょう。

pip install scikit-tda

そうすると、同梱されたripserパッケージが利用できるので、こんな分析が可能になります。

import numpy as np
from ripser import ripser
from persim import plot_diagrams
import matplotlib.pyplot as plt

# 例としてランダムなデータを生成
data = np.random.random((100, 2))  # 100点の2次元データ

diagrams = ripser(data)['dgms']

plot_diagrams(diagrams, show=True)

このコードは、100点の2次元ランダムデータを生成し、そのデータのパーシステントホモロジーを計算しています。ripser関数は、データセットのパーシステントホモロジーを計算し、plot_diagrams関数は計算されたパーシステントダイアグラムを表示します。

まとめ

いかがでしたでしょうか?トポロジカルデータ解析(TDA)は、ベッチ数など、データの形状やつながり方をトポロジーを用いて分析する手法です。上でちょっと出現したパーシスタントホモロジーという用語は、TDAの基本的な手法の一つであり、データの形状やつながり方を数値的に表現する方法の一つです。

パーシスタントホモロジーを用いることで、以下のような情報を取得することが可能となります。

  • データの連結成分の数
  • データの輪の数
  • データの空洞の数

これらの特徴を抽出することで、データの構造や性質を理解することができます。

生成AIを活用していく上で、埋め込みベクトルデータベースの状態を正しく把握することは、今後必須事項になります。いろんな手法を試行錯誤しながら、安定運用できるように方法を確立させていきたいと思っています!

今日で、RetailAI Advent Calendar 2023も最終日となりました。いろんな形で応援して頂き、投稿したメンバたちは、大変励みになったと思います。

これからも、テクノロジーを実運用に活かしながら、新しい未来を作っていくことに邁進していきます。

ありがとうございました!!!

参考文献

23
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
23
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?