Word2Vecで辞書を作成して見ました
By: Sharat Chinnapa
Tags: AI, 自然言語処理, 機械学習, Word2vec

このタスクは「文字レベル」、「単語レベル」、そして最近「文レベル」にもできるようになってます。

文字レベルと単語レベルの方はGloVeとWord2Vecなどの方法があります、今日はWord2Vecでシンプルな辞書をPythonで作って見ましょう。

注意: 自然言語処理では辞書の最適化によってタスクにかなりの改善も見られますが、今回は一旦デモができるレベルの辞書にはなれます。

必要な材料

パソコンで2–3GBぐらいの容量(cloudとColabでもできますが、今回はローカルにします)

以下のライブラリ

MeCab, wget, gensim, jaconv

import MeCab

import wget from gensim.corpora

import WikiCorpus from gensim.models

import Word2Vec from gensim.models.word2vec

import LineSentence

import jaconv from multiprocessing

import cpu_count import os VECTORS_SIZE = 50

wiki_file_name = 'jawiki-latest-pages-articles1.xml-p1p106175.bz2' ja_wiki_latest_url =

'https://dumps.wikimedia.org/jawiki/latest/jawiki-latest-pages-articles1.xml-p1p106175.bz2'

次元数は文字レベルの場合に20辺りでもいいかもしれませんが、単語レベルで行う際には50次元最低はオススメです。

その以下であれば(自分の経験で）言葉の意味が捕まえきれてないケースが多いです。

データを手に入れよう

さて、まずはデータを大量に必要ですので、wikipediaをダウンロードしましょう！

if not os.path.isfile(wiki_file_name):

wget.download(ja_wiki_latest_url, bar=wget.bar_adaptive)

今回は一部をダウンロードしています、役15分かかりました。全ての記事をダウンロードする場合は、3GBと3時間ぐらいが必要となります。

日本語の場合、同じ言葉や文字が全角か半角だったりするケースがあります。ローマジの場合、大文字と小文字のほとんどの場合に同じ意味を持つ(ｗａｔｅｒとwater) ここで、jaconvのライブラリを使い、すべてを全角に統一します。

def normalize_text(text):

return jaconv.h2z(text, digit=True, ascii=True, kana=True).lower()

半角に統一したい場合、jaconv.z2hとメソッドを利用できます。 辞書を利用する際、同じように統一する必要があります。

上記のメソッドを利用して、以前ダウンロードしたwikipediaデータを全角に変えながら、普通のtxtファイルに保存しましょう。

wiki_text_file_name = 'wiki.txt' def read_wiki(wiki_data, save_file):

if os.path.isfile(save_file):

print('Skipping reading wiki file...')

return

with open(save_file, 'w') as out:

wiki = WikiCorpus(wiki_data, lemmatize=False, dictionary={}, processes=cpu_count())

wiki.metadata = True

texts = wiki.get_texts()

for i, article in enumerate(texts):

text = article[0] # article[1] は記事名です

sentences = [normalize_text(line) for line in text]

text = ' '.join(sentences) + u'

'

out.write(text)

if i % 1000 == 0 and i != 0:

print('Logged', i, 'articles')

print('wiki保存完了') read_wiki(wiki_file_name, wiki_text_file_name)

ここでは、gensimのWikiCorpusを利用して簡単に解読できます。これで学習できるデータが揃いましたので次のステップに行きましょう。

単語トーケン作成

こちらはメカブの出番です。

def get_words(text: str, mt: MeCab.Tagger) -> List[str]:

mt.parse('')

parsed = mt.parseToNode(text)

components = []

while parsed:

if len(parsed.surface) >= 1: # EOSを覗くためにあります

components.append(parsed.surface)

parsed = parsed.next

return components

get_words のメソッドを利用して文書を単語(トーケン）に分けることができます。MeCabのparseToNode(text)メソッドの結果にはsurface とfeatureの二つのものがありますが、ここではsurfaceしか利用しません。

では、先ほど作成したwikipediaのデータをトーケン化しましょう。

token_file = 'tokens.txt' def tokenize_text(input_filename, output_filename, mt):

if os.path.isfile(output_filename):

print('出力ファイルがすでに存在しています。')

return

with open(output_filename, 'w') as out:

with open(input_filename, 'r') as data:

for i, text in enumerate(data.readlines()):

tokenized_text = ' '.join(get_words(text, mt))

out.write(tokenized_text)

if i % 1000 == 0 and i != 0:

print('Tokenized ,', i, 'lines')

print('トーケン作成完了')



tagger = MeCab.Tagger('-d /usr/local/lib/mecab/dic/mecab-ipadic-neologd') #neologd がなければ、別なものを使ってもOK

tokenize_text(wiki_text_file_name, token_file, tagger)

Wikipediaの記事ごとをトーケンに変え、半角スペースを入れ、またファイルに出力しています。メモリーにもつのもありかもしれませんが、RAMを結構使うケースが多いために、ファイルに出力させていただいてます。

ベクトル化

いおいおベクトル作成の時がきました。コード的には簡単にかけます。

vector_file = 'ja-MeCab-50.data.model'

def generate_vectors(input_filename, output_filename):

if os.path.isfile(output_filename):

return

model = Word2Vec(LineSentence(input_filename),

size=VECTORS_SIZE, window=5, min_count=5,

workers=cpu_count(), iter=5)

model.save(output_filename)

print('ベクトル作成完了。') generate_vectors(token_file, vector_file)

GensimのWord2Vecで、上記のように定義された50次元のベクトルが作成されます。min_count_は辞書に含まれるための最低回数です。使ってるデータに応じて編集してみてください。

ベクトル作成もかなりの時間かけますので、ローカルで行う場合、一晩中学習させてもらう感じではオススメです。また、google datalabやawsで実装してみた方が良いかもしれません。

お試しタイム！

これで作成できましたので、どうやって使えばいいのか、、

from gensim.models import load_model model = load_model(vector_file)

model = model.wv print(model['東京'])

print(mm.most_similar(positive='東京', topn=5))

で試してみてください！

辞書の結果、多少違っても大丈夫です

今回はベクトル辞書の作成について説明いたしました。wikipediaのデータで学習し、MeCabを利用してトーケン化して、最後にWord2Vecのベクトル辞書の作成を行いました。

この辞書の結果がEmbeddingとしてニューラルネットにも使えます。でもそちらはまた別に機会に。

トップの写真はこちらからいただきました: https://www.pexels.com/photo/black-and-white-book-business-close-up-267669/

また、こちらも参考になりました。

今回のコードは以下です