【機械学習】gensimのチュートリアルをやってみた(その2)
さて、その1の続きを書きます。
ディクショナリーへの登録を行います。
Pythonで辞書をforで作成する際「キーがー存在する場合はバリューを更新」「存在しない場合はキー:バリューを追加」したい場合は標準ライブラリのdefaultdictを使うのが良いそうです。
まずは初期化のおまじないです。
from collections import defaultdict frequency = defaultdict(int)
現在の変数textsの中身は以下のようになっています。
[['human', 'machine', 'interface', 'lab', 'abc', 'computer', 'applications'], ['survey', 'user', 'opinion', 'computer', 'system', 'response', 'time'], ['eps', 'user', 'interface', 'management', 'system'], ['system', 'human', 'system', 'engineering', 'testing', 'eps'], ['relation', 'user', 'perceived', 'response', 'time', 'error', 'measurement'], ['generation', 'random', 'binary', 'unordered', 'trees'], ['intersection', 'graph', 'paths', 'trees'], ['graph', 'minors', 'iv', 'widths', 'trees', 'well', 'quasi', 'ordering'], ['graph', 'minors', 'survey']]
この中のそれぞれの文字の出現回数をカウントします。二次元配列なのでfor文を入れ子にします。
for text in texts: for token in text: frequency[token] += 1
この段階での配列frequencyの中身は以下のようになっています。
文字と出現回数が結びついていますね。
defaultdict(<class 'int'>, {'abc': 1, 'error': 1, 'iv': 1, 'widths': 1, 'testing': 1, 'survey': 2, 'eps': 2, 'opinion': 1, 'intersection': 1, 'time': 2, 'minors': 2, 'machine': 1, 'well': 1, 'interface': 2, 'measurement': 1, 'ordering': 1, 'management': 1, 'graph': 3, 'human': 2, 'user': 3, 'computer': 2, 'applications': 1, 'relation': 1, 'binary': 1, 'generation': 1, 'lab': 1, 'quasi': 1, 'trees': 3, 'unordered': 1, 'response': 2, 'paths': 1, 'engineering': 1, 'random': 1, 'system': 4, 'perceived': 1})
この中で出現回数が1回だけのものは除く処理を行います。
texts = [[token for token in text if frequency[token] > 1] for text in texts]
これで変数textsの中身が以下のようになりました。
[['human', 'interface', 'computer'], ['survey', 'user', 'computer', 'system', 'response', 'time'], ['eps', 'user', 'interface', 'system'], ['system', 'human', 'system', 'eps'], ['user', 'response', 'time'], ['trees'], ['graph', 'trees'], ['graph', 'minors', 'trees'], ['graph', 'minors', 'survey']]
そして、gensimの特徴語ディクショナリーを作成します。
dictionary = corpora.Dictionary(texts) dictionary.save('/tmp/deerwester.dict') # ディクショナリーを保存します print(dictionary.token2id)
出力される値が以下のように配列textsのキーに対してidが割り振られています。
{'human': 1, 'user': 5, 'computer': 2, 'survey': 4, 'eps': 8, 'time': 7, 'system': 6, 'response': 3, 'interface': 0, 'minors': 11, 'trees': 9, 'graph': 10}
これらの配列をgensimのBug of Wordsで各文の特徴語をカウントして特徴ベクトルを作ります。
先ほど作成した特徴語ディクショナリーにdoc2bowメソッドにより、文の単語に一致するidと出現頻度をタプルで返してくれます。
これにより、類似したcorpusを検索することで、それっぽい言葉を取り出せるものと思う。
corpus = [dictionary.doc2bow(text) for text in texts] corpora.MmCorpus.serialize('/tmp/deerwester.mm', corpus) #後で使えるように保存(corpusは膨大になってしまうため) print(corpus)
出力結果は以下のようになります。
[[(0, 1), (1, 1), (2, 1)], [(2, 1), (3, 1), (4, 1), (5, 1), (6, 1), (7, 1)], [(0, 1), (5, 1), (6, 1), (8, 1)], [(1, 1), (6, 2), (8, 1)], [(3, 1), (5, 1), (7, 1)], [(9, 1)], [(9, 1), (10, 1)], [(9, 1), (10, 1), (11, 1)], [(4, 1), (10, 1), (11, 1)]]
よし、これで基本的な動かし方は分かったぞ。。。