単語埋め込みのライブラリ whatlies を調べてみた

NLP
この記事は約10分で読めます。

先日、Twitterでtransformersとscikit-learnをscikit-learnのPipelineを使って組み合わせることができることを知りました。

構成としては、transformersのモデルの最終層のアウトプットを特徴量としてscikit-learnのモデルに渡すというよくあるパターンだと思うのですが、transformersのモデルから出力を得るところで使用されているwhatliesというライブラリがかなり便利だと思ったので紹介します。

whatliesとは?

whatliesは、”What lies in word embeddings?”というコンセプトで作成されており、単語埋め込みに関するライブラリです。

GitHubのスター数は、執筆時点では371でそれほど知名度が高いわけではないですが、単語埋め込みは扱うことが多いので、活用方法を知っておいて損はないと思い、調べてみました。

GitHub

GitHub - koaning/whatlies: Toolkit to help understand "what lies" in word embeddings. Also benchmarking!
Toolkit to help understand "what lies" in word embeddings. Also benchmarking! - GitHub - koaning/whatlies: Toolkit to help understand "what lies...

公式ドキュメント

whatlies
A python package to discover

何ができるのか

ここからは、このライブラリで具体的に何ができるのかについて、簡単に紹介します。

できることは大きく分けると2つで、単語埋め込みをインタラクティブ形式で可視化できること、そして先ほど少し言及した、様々なモデルの単語埋め込みを簡単にscikit-learnのモデルの特徴量として使えることです。

単語埋め込みをインタラクティブ形式で可視化できる

https://github.com/koaning/whatlies より

単語埋め込みを平面にプロットして、インタラクティブに操作することができます。plotlyを使うことでも、同じようなことが実現できますが、emb.plot_interactive() を使うだけで簡単に実現できるのが魅力の1つだと思います。また、上のgifはそれぞれの単語をx軸を”man”、y軸を”woman”として関係性をプロットしていて、少し凝ったこともできるようになっています。

scikit-learnのモデルの特徴量として使える

transformers以外にも、有名どころだとspaCyやGensimのモデルなども扱うことが可能です。現時点では、下記のモデルに対応しているようです。

使い方

実際に動かしてみます。使用したnotebookはこちらから確認いただけます。

whatlies: Introduction
Explore and run machine learning code with Kaggle Notebooks | Using data from w2v google news 300

インストール方法

whatlies
A python package to discover
# 最小限の機能
pip install whatlies

# spacyやtransformersのモデルを扱いたい場合
pip install whatlies[spacy]
pip install whatlies[transformers]

# 全部盛り
pip install whatlies[all]

単語埋め込みを可視化する

What Are Embeddings - whatlies
A python package to discover
Interactive Visualisation - whatlies
A python package to discover

今回は、使用する機会が多いGensimのword2vecを使用します。

from whatlies.language import GensimLanguage

# GensimLanguageはkv形式のモデルしか対応していない点に注意
model = GensimLanguage('/path/to/xxxxx.kv')

矢印で可視化

model['man'].plot(kind="arrow", color="blue")
model['woman'].plot(kind="arrow", color="red")
model['king'].plot(kind="arrow", color="blue")
model['queen'].plot(kind="arrow", color="red")
plt.axis('off')
それぞれの単語の関係性を矢印で可視化できます
model['man'].plot(kind="arrow", color="blue")
model['woman'].plot(kind="arrow", color="red")
model['king'].plot(kind="arrow", color="blue")
model['queen'].plot(kind="arrow", color="red")

(model['king'] - model['man'] + model['woman']).plot(kind="arrow", color="pink")

plt.axis('off')
king – man + womanの矢印をピンク色で表示

このように、ベクトルの足し引きの結果を表示することも可能です。king – man + womanがqueenのベクトルと近いことが確認できます。

散布図で可視化

GitHubのREADMEに掲載されていたgifは以下のコードで再現できます。

# 可視化したい単語を指定
words = ["prince", "princess", "nurse", "doctor", "banker", "man", "woman",
         "cousin", "neice", "king", "queen", "dude", "guy", "gal", "fire",
         "dog", "cat", "mouse", "red", "blue", "green", "yellow", "water",
         "person", "family", "brother", "sister"]
# 単語埋め込みを取得
emb = model[words]

# 可視化(x軸をman, y軸をwoman)
emb.plot_interactive('man', 'woman')

次元を指定してプロットすることも可能です。

# 可視化(x軸を次元0, y軸を次元1)
emb.plot_interactive(x_axis=0, y_axis=1)

PCAやUMAP、t-SNEを使用して次元削減したものを可視化することも簡単にできます。

from whatlies.transformers import Pca, Umap

pca_emb = emb.transform(Pca(2))
umap_emb = emb.transform(Umap(2))
plot_pca = pca_emb.plot_interactive()
plot_umap = umap_emb.plot_interactive()
plot_pca | plot_umap
左がPCA、右がUMAP

ヒートマップで可視化

単語埋め込みのコサイン類似度をヒートマップで可視化する機能もあります。

# metricは'cosine'と'correlation'が選択可能
emb.plot_similarity(metric="cosine")

scikit-learnのモデルに特徴量として使う

Scikit-Learn Compatibility - whatlies
A python package to discover

今回は、Hugging Face datasetsを使ってIMDbデータセットをダウンロードして学習と推論を行ってみます。

# IMDbデータセットの準備
import datasets
import pandas as pd

imdb = datasets.load_dataset('imdb')
train_df = pd.DataFrame(imdb['train'])
test_df = pd.DataFrame(imdb['test'])

これでデータセットが準備できたので、先ほど用意したword2vecのモデルとLGBMClassifierを使って学習してみましょう。

from sklearn.pipeline import Pipeline
from whatlies.language import GensimLanguage
from lightgbm import LGBMClassifier

# pipelineを作成
pipe = Pipeline([
    ("embed", GensimLanguage('/path/to/xxxxx.kv')),
    ("model", LGBMClassifier())
])

# 学習
pipe.fit(train_df['text'].tolist(), train_df['label'].tolist())

推論を行い、精度を確認しましょう。

# 推論
test_pred = pipe.predict(test_df['text'].tolist())

# 精度の確認
from sklearn.metrics import classification_report

print(classification_report(test_df['label'].values, test_pred))

今回は、word2vec + LGBMでしたが、参考にした以下のnotebookのようにtransformersのモデルを使用することも可能です。

Scikit-learn with Transformers
Explore and run machine learning code with Kaggle Notebooks | Using data from No attached data sources

おわりに

今回は、単語埋め込みに関するライブラリであるwhatliesについて紹介しました。インタラクティブに可視化できたり、scikit-learnのPipelineに組み込んで使える点は、実用性がかなりあると思うので、これからお世話になることも多いのではないかと考えています。

最後まで、ご覧いただきありがとうございました。

コメント

タイトルとURLをコピーしました