簡単な関連ワード検索システムを想定しながらWord2Vecの紹介

簡単な関連ワード検索システムを想定しながら、なるべく難しい話を入れずに、Word2Vecを紹介したいと思います。

ここに、`"dog"`（犬）、 `"bird"`（鳥）、 `"cat"`（猫） という3つの単語があるとします。
Word2Vecを使うと、「`"dog"と"cat"`の関係の方が、`"dog"と"bird"`や`"cat"と"bird"`の関係よりも類似度が高い」という判定ができるようになります。

Word2Vecは、大量のテキストデータを読み込んで機械学習し、単語の意味を数値化します。
よって、何をもって類似度が高いとするかは学習したデータに依存します。

さらに、単語の意味を数値化しているので、単語の足し算や引き算が出来るようになります。
以下は、Word2Vecの紹介でよく利用される有名な例です。

`"king" - "man" + "woman" = ?`

`"king"`(王様)という単語から`"man"`（男性）という単語を引き、`"woman"`(女性)という単語を足したら、どんな単語が出てくるでしょうか？
Wikipediaの記事を学習させたWord2Vecの場合、`"queen"`(女王)という単語が得られます。

このような事が出来るのが、Word2Vecです。

### Word2Vecを使った簡単な関連ワード検索システムを想定してみる
ここでは画像をキーワードで検索するシステムを想定してみます。

まず、検索対象となる画像に対してタグを付けます。
例えば犬の画像であれば`"dog"`を、猫の画像であれば`"cat"`とう具合にタグ付けを行います。
タグが、入力された検索キーワードと完全一致する画像を検索結果に表示する仕組みを作れば、シンプルな画像検索システムの出来上がりです。

ただ、これだと完全一致する画像しか出てこないので、関連するワードでの検索結果もサジェストしたいと思います。
そこで、Word2Vecを利用して、入力された検索キーワードの類似語を得るようにします。
例えば、入力された検索キーワードが`"dog"`の場合、Word2Vecから得られた`"dog"`の類似語は以下となります。

| Word | 意味 | distance |
|:-:|:-:|:-:|
|spaniel|スパニエル|0.638096|
|dogs|犬(複数形)|0.632835|
|hound|猟犬(フォックスハウンド)|0.601802|
|terrier|テリア|0.582280|
|hounds|猟犬(フォックスハウンド)|0.562277|
|borzoi|ボルゾイ|0.561244|
|hund|ダックスフント|0.560709|
|bonzo|ボンゾ|0.558554|
|sighthound|サイトハウンド|0.552112|
|mastiff|マスチフ|0.535340|
|foxhound|フォックスハウンド|0.533682|
|sleds|そり|0.532323|
|badger|アナグマ|0.528601|
|spitz|スピッツ|0.526312|
|bolonka|ボロンカ|0.521960|
|pinscher|ピンシャー|0.517604|
|greyhound|グレーハウンド|0.511010|
|keeshond|キースホンド|0.508404|
|dachshund|ダックスフント|0.506582|
|poodle|プードル|0.504815|
|wag|(しっぽなどを)振る|0.501827|
|cur|のら犬|0.500876|
|sheepdog|牧羊犬|0.499927|
|cat|猫|0.498055|
|puppy|子犬|0.494615|
|ibizan|イビザン|0.493629|
|inu|(日本語？)|0.491278|
|keeshonden|キースホンド|0.488974|
|familiaris|ファミリアス|0.488221|
|collie|コリー|0.487947|
|retriever|レトリーバー|0.486032|
|apso|アプソー|0.482635|
|wirehaired|ワイアーヘアード|0.481742|
|pet|ペット|0.478147|
|catahoula|カタフーラ|0.478084|
|canidae|イヌ科|0.477117|
|coonhound|クーンハウンド|0.475645|
|pictus|ピクタス|0.474126|
|wolfhound|ウルフハウンド|0.473700|
|wolfhounds|ウルフハウンド|0.469465|

　　　　　　　　　　　　　・
　　　　　　　　　　　　　・
　　　　　　　　　　　　　・

犬種に関するワードが多いですね。
これらの単語もキーワードとして検索すると`"dog"`というキーワードから、より広範囲のタグ検索や、表記揺れへの対応が出来そうです。

面白いのは、`"sleds"`(そり)という単語が上位に来ています。
`"dog"`で検索した人が、そりの検索結果を求めているかどうかは微妙ですが、関連しているのにユーザーが想定していなかったワードの可能性もあるので、そういったものを含んだ検索結果をサジェストできそうです。

distance列の数字が関連度合いを示していて、値はWord2Vecから取得できます。
`0.5以上`などの閾値を決めることで、検索する範囲が広がりすぎないよう絞ることが出来ます。
スライダーでユーザー自身が調整できるようにしても面白いですね。

### 単語の演算を取り入れてみる
Word2Vecでは単語の足し算・引き算が出来ました。

例えば、以下の演算をすると、どのような単語が得られるでしょうか？

`"france" - "japan" + "tokyo" = ?`

試してみた結果、"paris"(パリ)という単語が最上位となりました。
パリと言えば、フランスの首都ですね。
この演算では、`フランス`から`日本`を引いて`東京`を加えた事になりますが、見方を変えると、
「`日本と東京の差`を`フランス`という単語に加えた」とも言えるかと思います。

つまり、`"france"`の部分を別の国の名前に置き換えても同じ効果が得られます。
```
"france"  - "japan" + "tokyo" = "paris"(パリ)
"germany" - "japan" + "tokyo" = "berlin"(ベルリン)
"russia"  - "japan" + "tokyo" = "moscow"(モスクワ)
"spain"   - "japan" + "tokyo" = "toledo"(トレド)
"china"   - "japan" + "tokyo" = "shanghai"(上海)
```
色々な国名で試してみた所、首都は上位に入ってきますが、必ずしも最上位というわけではありませんでした。
しかし、有名な都市が常に上位に現れるので、これは立派な「主要都市検索機能」といえるかと思います。
この仕組みを使えば、ユーザーが国の名前を検索すると、主要都市でタグ付けされた画像も検索候補に含めるといった機能を提供できそうですね。

この仕組みを理解するために、もう一つ例を上げます。
以下は、各単語から`book`を引いて`books`を加えた結果です。
```
"pencil"    - "book" + "books" = "pencils"
"car"       - "book" + "books" = "cars"
"company"   - "book" + "books" = "companies"
"companies" - "book" + "books" = "subsidiaries"(子会社)
"money"     - "book" + "books" = "funds"(ファンド)
"japanese"  - "book" + "books" = "japan"(日本)
```
これは、`"books"と"book"の差`を特定の単語に加えた形になります。
`"books"と"book"の差`は複数形か単数形かの違いしかありません。
その違いを単数の単語に加えることで、その単語の複数形を得ることが出来ます。

ちなみに、既に複数形の単語（`"companies"`）や、単数形でも複数形でも形が変化しない単語（`"money"`、`"japanese"`）に対して行った場合、それっぽい別の単語を無理やり返す所は、なんとなくAIっぽいですね。

### Word2Vecを使ったサービス
実際に検索サービスを構築するには、学習データのチューニングなど苦労する所も多くあると思いますが、既に以下のような様々な分野で利用されており、有用なツールであることは間違いありません。

- レコメンデーション
- 文章要約
- 文章生成
- 機械翻訳
- 口コミやレビューの分析

「口コミやレビューの分析」では、文章の感情分析にWord2Vecが利用されます。
投稿されたメッセージ内の各ワードが「怒り、嫌悪、恐れ、幸福、悲しみ、驚き」を表す単語とどのくらいの距離があるかで、これがクレームなのか高評価のレビューなのかといった分析が自動的に行なえます。

興味のある方は、是非、触れてみて下さい。