赤飯にかかったアレ

雑多なメモ帳

chainerで論理演算XORの学習 [chainer練習中、結果は多分間違ってる]

ChainerCVという画像処理に特化したものがあるらしい

github.com

やりたいなぁ、なんかサンプルもいっぱいあるし

ChainerCV Tutorial — ChainerCV 0.10.0 documentation

ただ、その前にchainerで遊びます。

練習を兼ねて交差エントロピー誤差を使いXORの学習をしてみました。

学習とテスト用のデータを一緒にして露骨に過学習させてみます。(やってみたかっただけ)

以下ソース+コメントによる補足

'''
論理演算XORの学習

使ったバージョン
python 3.6.6

numpy 1.15.0
Pillow 5.2.0
chainer 4.2.0
tqdm 4.24.0
'''
import numpy as np
import chainer
import chainer.functions as F
import chainer.links as L
import chainer.initializers as I
from chainer import training
from chainer.training import extensions

'''
# バージョンの確認
from pkg_resources import get_distribution
import platform
print('python', platform.python_version())
print("")
libs = ['numpy', 'Pillow', 'chainer', 'tqdm']
for lib in libs:
version = get_distribution(lib).version
print(lib, version)
'''

# ニューラルネットの構造を設定する
# 入力2(l1)に対して中間層は3つ。ここでRelu関数で処理を行ってh1とする
# 出力2をyとしてreturn
class MyChain(chainer.Chain):
 
def __init__(self):
super(MyChain, self).__init__()
with self.init_scope():
self.l1 = L.Linear(2, 3) # 入力2、中間層3
self.l2 = L.Linear(3, 2) # 中間層3、出力2
def __call__(self, x):
h1 = F.relu(self.l1(x)) # Relu関数
y = self.l2(h1)
return y

epoch = 1000 # 学習回数
batchsize = 4 # ミニバッチサイズ
# ミニバッチ学習用の学習データをいくつかのサイズに分割しておき、その分割された少量のサンプルを使用してニューラネットワークのパラメータを更新する
# ミニバッチサイズが1の場合をオンライン学習、ミニバッチサイズが学習データのサイズと一致する場合をバッチ学習という
# バッチサイズは大きいほど学習が高速化するが収束しなくなるので注意

# データの作成
# 入力データ、出力データはリスト形式で設定、学習データは2次元行列、テストデータは1次元の行列とする
trainx = np.array(([0,0], [0,1], [1,0], [1,1]), dtype=np.float32)
trainy = np.array([0,1,1,0], dtype=np.int32)
# 学習データとテストデータに同じものを使用
train = chainer.datasets.TupleDataset(trainx, trainy)
test = chainer.datasets.TupleDataset(trainx, trainy)

# ネットワークの登録
'''
ネットーワークの登録方法
2. 最適化関数の設定
3. モデルの設定
'''
model = L.Classifier(MyChain(), lossfun=F.softmax_cross_entropy)
# chainer.serializers.load_npz('result/out.model', model)
# 2. 最適化関数の設定 教師データと計算した結果の誤差をどのように学習していくのかを決める関数
optimizer = chainer.optimizers.Adam() # 最適化関数の設定
# 3.作成したオプティマイザにモデルを設定する
optimizer.setup(model)

# イテレータの定義
# 学習データとテストデータの作成
train_iter = chainer.iterators.SerialIterator(train, batchsize) # 学習データ
test_iter = chainer.iterators.SerialIterator(test, batchsize, repeat=False, shuffle=False) # 評価データ
# アップデータの登録
# 学習データとオプティマイザを結びつける
updater = training.StandardUpdater(train_iter, optimizer)

# 学習環境の設定と学習回数の設定
trainer = training.Trainer(updater, (epoch, 'epoch'))

# 学習状況の表示
trainer.extend(extensions.LogReport()) # ログ
trainer.extend(extensions.Evaluator(test_iter, model)) # エポック数の表示
trainer.extend(extensions.PrintReport(['epoch', 'main/loss', 'validation/main/loss','main/accuracy', 'validation/main/accuracy', 'elapsed_time'] )) # 計算状態の表示

# ニューラルネットワークの構造の可視化
# できた.dotファイルをgraphvizをインストールしてpng形式に変換する。コマンドは以下
# dot -K dot -T png cg.dot -o cg.png
trainer.extend(extensions.dump_graph('main/loss')) # ニューラルネットワークの構造

# 精度のグラフ表示
# 縦軸:精度
# 横軸:エポック数
trainer.extend(extensions.PlotReport(['main/accuracy', 'validation/main/accuracy'],'epoch', file_name='accuracy.png')) # 精度のグラフ

# 誤差のグラフ表示
# 縦軸:交差エントロピー誤差
# 横軸:エポック数
trainer.extend(extensions.PlotReport(['main/loss', 'validation/main/loss'], 'epoch',file_name='loss.png')) # 誤差のグラフ

# 学習状況の保存
trainer.extend(extensions.snapshot(), trigger=(100, 'epoch')) # 学習再開のためのスナップショット出力

# chainer.serializers.load_npz("result/snapshot_iter_100", trainer) # 再開用
# chainer.serializers.save_npz("result/out.model", model)

# 学習の開始
trainer.run()

 

実行結果、

epoch       main/loss   validation/main/loss  main/accuracy  validation/main/accuracy  elapsed_time

1           0.746678    0.745468              0.5            0.25                      0.00873882    

2           0.745468    0.744273              0.25           0.25                      0.0130902     

3           0.744273    0.743095              0.25           0.25                      0.0170885 

.

.

637         0.638736    0.638492              0.75           0.75                      9.54412       

638         0.638492    0.638247              0.75           0.75                      9.56882       

639         0.638247    0.637993              0.75           0.75                      9.60504       

640         0.637993    0.637751              0.75           1                         9.63925       

641         0.637751    0.637499              1              1                         9.67876       

642         0.637499    0.637259              1              1                         9.70237       

643         0.637259    0.637006              1              1                         9.7315    

.

. 

998         0.506556    0.506092              1              1                         19.85         

999         0.506092    0.505668              1              1                         19.8964       

1000        0.505668    0.505221              1              1                         19.9257     

 

精度(accuracy)が途中で100%になったのでなんかできてる感じがします。

それではグラフで表示してみます。

 

精度のグラフ表示
縦軸:精度
横軸:エポック数

accuracy.png

f:id:sekihan_0290:20180817213258p:plain

僕、精度って上がっていくようなきがするんだ(なんか変)

 

誤差のグラフ表示
縦軸:交差エントロピー誤差
横軸:エポック数

loss.png

f:id:sekihan_0290:20180817213356p:plain

学習を進めるにつれて値が小さくなっているから学習はできてると考えていいはず

ただ精度が・・・むむむ

 

太宰治の文章からボットを作る

 マルコフ連鎖の練習も兼ねて
マルコフ連鎖を使用した対話モデルを作って遊んでます。

(マルコフ連鎖とその学習のやり方は、ほぼ以下の書籍の写経です)

マルコフ連鎖とは

 マルコフ連鎖は確率過程の一つと考えていいのかな

  • 別名マルコフ過程
  • 確率過程を使って文章をつなぎ合わせて文を作る
  • マルコフ性(次に予測される状態が過去の状態に依存せず、現在の状態によってのみ決まる性質)を持つ確率過程のうち取り売る値が離散的なもの(マルコフ性を備えた確率過程を総称したマルコフ過程の中でも取る可能性のある値が連続的でなく離散的)これを特にマルコフ連鎖という・・・らしいよ

文の類似度を調べるN-gramの基本原理ってことでいいかな

 

次に来る文字を予測するLSTMでも試したけど、こっちの方が意味が通じる
パラメータ調整をミスってるのもあると思うけど、学習に時間かかりすぎるので却下

続きを読む

AIに文章を書かせたい! [Keras-LSTMサンプルコードで太宰治に文章を書かせたい]

機械の文章力の成長過程が見たい!!

テキストマイニングがしたい! part3. ディープラーニング幼稚園児の文章生成編 [Keras-LSTM文字生成サンプルコード] - 赤飯にかかったアレ

の続きです。

前は

  • 使ったテキストが少なかった(短編1作品のみ)
  • 形態素解析してない文章を使っていた
  • 理解度0でサンプルコード実行しただけ(今回もだけど...)

太宰治の文章をMeCab分かち書きし、KerasのLSTMサンプルコードにちょっと手を加えて文章を生成します。

ついでにWord2Vecでモデルも作ってみます。

 

機械の文章力の成長過程が見たい!!

ジュババァって機械動くの気持ちいいよね

 

あっ!ついでだけど芥川龍之介でこれやったら芥川賞クラスの文になるのかな? 試せたら試そう。

# 念のため_______________

AIという言葉は、色々な解釈ができると思います。

僕のAIの定義は学習し、判断できるものです。

今回は、

  • 事前に文章から辞書を作る。
  • テキストをベクトル化する、モデルを作る。
  • 学習して文章を生成する。

ということを行います。

学習と判断を行うため、タイトルにAIを入れました。

これをみっちゃった人のAIの定義と違ってたらごめんね

 _________________

続きを読む

テキストマイニングがしたい! part4.word2vec用のモデル作成

こんなことができるモデルを作ります。 

word2test.pyの実行結果

金魚 = 余,まし,曲,表面,これ,勝利,あれ,見付け,実,研究生
生命 = 溢れ,名品,例,美事,理想,なり,失敗,財政,死ぬ,絢爛
作る = 普通,神秘,調べ,一緒,華鬘,進ん,出し,来,遣り繰り,それ
Word2Vec(vocab=1337, size=100, alpha=0.025) = 普通,神秘,調べ,一緒,華鬘,進ん,出し,来,遣り繰り,それ

に ニ に 助詞-格助詞-一
続きを読む

テキストマイニングがしたい! part3. ディープラーニング幼稚園児の文章生成編 [Keras-LSTM文字生成サンプルコード]

機械に文章を書かせたい!

これを見つけてしまいそういう頭になってしまった。

今学習中でワクワクでテンション高いです。

以降本題、

 

 Kerasには文章生成のサンプルコードがあります。

github.com

 しかも、それを日本語で解説してくれている方がいました。

qiita.com

さらに、その中でリファクタリングしたものまで用意されてました。 

https://github.com/YankeeDeltaBravo225/lstm_text_generation_comment/blob/master/lstm_text_generation_refactored.py

 

これをそのまま実行しよう!

と思ったのですが、使う文章がニーチェの文集。しかも英語。

 あいにく幼稚園児なので英語は読めないし、時間もないので哲学も苦手です。

 

KerasのLSTMサンプルコードを日本語の文章で生成しようぜ!(前置き長い)

続きを読む