粗大メモ置き場

個人用,たまーに来訪者を意識する雑記メモ

KerasのバックエンドがTheanoから変更できなくなった話

結論

結論から言うと
~\.keras.jsonを見るだけでなく,
keras_activate.batの存在にも注意した方がいいです。

Kerasのバックエンドの変え方

KerasのバックエンドはTheanoかTensorflowか選べます。
中身はたいていユーザ直下の「.keras\keras.json」を弄れば解決します。

公式の通りにやればいいでしょう。
バックエンド - Keras Documentation


ただ,今回ハマった問題としてここを変更したにもかかわらず
backendがTheanoに固定されていた問題に一時間ほど悪戦苦闘しました。

それでもうまくいかない場合

私の場合,仮想環境を立ち上げた際に次のコマンドが出力されていました。
どう見てもデフォルトバックエンドをtheanoに固定しに来ています。
許せん。

\Anaconda3\envs\tf35\etc\conda\activate.d>set "KERAS_BACKEND=theano"

どう見てもこのファイルが怪しいので現地へと調査しにいきました。
f:id:ossyaritoori:20170601225237p:plain

今回インタビューをするのは「keras_activate.bat」さん。
中身を見ると…

set "KERAS_BACKEND=theano"

はいギルティー。

set "KERAS_BACKEND=tensorflow"

上記のように書き換えておきましょう。

Kerasを用いた手書き画像認識Ⅲ:畳み込みネットワークを用いたテストコード

前回までのあらすじ

最初はTensorflowを用いて隠れ層を導入したパーセプトロンにて学習を行いました。
ossyaritoori.hatenablog.com


次に,Kerasを導入して3層のニューラルネットワークで学習を行い,改善を得ました。
ossyaritoori.hatenablog.com

今回は畳み込みニューラルネットワークを試してみましょう。



畳み込みネットワーク(CNN)について

画像の認識などにおいて強力な性能を発揮する手法で、
画像の二次元畳み込み(2D Convolution)計算を層間の伝搬に用いる手法です。
以下のサイトが図が見やすくてわかりやすいでしょう。
postd.cc

最近聞いてきた公演によるとプーリング層や全結合層はなくて,GAP層を用いるのが標準になりつつあるそうですね。

環境の下準備

前回の記事でのKerasパッケージの導入のところをきちんとこなしておいてください。
Tensorflow,Kerasを用いた手書き画像認識:MNISTを使ったテストコード - 粗大メモ置き場

KerasにおけるCNNの実装手法

以下にKerasを用いた際のモデルの生成部を示します。
Denseの代わりにConv2Dという関数で畳み込みの層を決めており,
Kernelのサイズや数などを同時に決定しています。

これだけです。まじかよ超簡単じゃん。

model = Sequential()
model.add(Conv2D(32, kernel_size=(3, 3),
                 activation='relu',
                 input_shape=input_shape))
model.add(Conv2D(64, (3, 3), activation='relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
model.add(Dropout(0.25))
model.add(Flatten())
model.add(Dense(128, activation='relu'))
model.add(Dropout(0.5))
model.add(Dense(num_classes, activation='softmax'))

model.compile(loss=keras.losses.categorical_crossentropy,
              optimizer=keras.optimizers.Adadelta(),
              metrics=['accuracy'])

流れは,

  • 32カーネル 畳み込み層(ReLu)
  • 64カーネル 畳み込み層(ReLu)
  • プーリング層
  • 128要素の全結合相?
  • 10クラスへの出力層

と言ったところでしょう。


例のごとく他所様からコードをお借りしていますが疑問として,
どうして最初の層が32個のカーネルなのに次の層が64個なんでしょう?
(勉強不足が露呈している)

なんとなく逆の方が良さそうなもんですが何か意味があるんでしょうか。

Kerasを用いたコード

ライブラリとしてKerasをダウンロードしたPC上で動作を確認しています。
実行環境はSpyder3上のIPythonコンソール上で行っています。

詳しい環境については過去記事を漁ってください。


結果:元のコード

数回のEpochを繰り返して精度をブラッシュアップしますが今回は12回目で99%を達成しました。これだけでも十分すごいですが実用上では99.999%より上の性能が求められるようでなんというか大変だなぁ…

Epoch 12/12
60000/60000 [==============================] - 82s - loss: 0.0365 - acc: 0.9887 - val_loss: 0.0289 - val_acc: 0.9901
Test loss: 0.0288566211587
Test accuracy: 0.9901

結果:ちょっと弄ったコード

さっきの畳み込み層の順番を32→64から64→32へと変更してみました。
ほとんど差がありませんね。ただ,かかった時間はこちらのほうが長かったように思います。
確かより「深い層」の方が計算が面倒になるのでそういった事情を考慮して32→64という構造なのかもしれません。

Epoch 12/12
60000/60000 [==============================] - 102s - loss: 0.0450 - acc: 0.9869 - val_loss: 0.0287 - val_acc: 0.9904
Test loss: 0.0286987099324
Test accuracy: 0.9904

後処理

モデルの保存

せっかく作ったモデルですのでもったいないしきちんと保存しましょう。
[TF]KerasでModelとParameterをLoad/Saveする方法 - Qiita

jsonという形式を通してファイルで保存したいとすると,以下のような流れになります。
詳細は今度記事に書きます。pickleというクラスを使います。

import pickle
json_string = model.to_json()
with open('mnistmodel.pickle', 'wb') as f:
    pickle.dump(json_string,f)

学習したパラメータの保存

学習したパラメータは.hdf5という形式で保存されます。

model.save_weights('mnistparam.hdf5')

読み出し方は上のURLを参照してください。個別に記事を書くかもしれません。

可視化

可視化についてはgraphvizやらpydot_ngやらをインストールする必要があるのでまた今度書きます。
以下のサイトが役に立つことでしょう。
www.mathgram.xyz

感想

とりあえず一連の記事をもってMNISTのテストはここらへんで終了ということにしようと思います。感想として複雑な学習をするにはGPUが必須という所感を受けました。

今回のMNISTの学習では大体18分くらいかかっていましたが,コードを書いた人によるとGPUを積んだPCだと大体その1/5弱の3~4分で終えることができるそうです。

これから機械学習を始める人は是非GPUをきちんと積んだPCを使うのが良いでしょう。




Tensorflow,Kerasを用いた手書き画像認識Ⅱ:多層ニューラルネットを用いたテストコード

記事の前提

前回は隠れ層を入れたパーセプトロンを用いて手書き画像の認識を行いました。
ossyaritoori.hatenablog.com

Kerasとは

Python上で動作する深層学習用のライブラリのことです。
TensorflowやTheanoと言ったライブラリを前提にしていて,それらを用いてより高い抽象度で計算を書けるようです。

まぁつまり,「簡単」ってこと!!!(せやろか)

深層学習ライブラリ Keras - 人工知能に関する断創録
Python製深層学習ライブラリ「Keras」の紹介 (with TensorFlow) - amacbee's blog

Kerasの環境構築1

実は,Tensorflow1.0以降を入れている場合はKerasはモジュール?の一部として入っているようです。
今のところこっちで特に問題はなさそうな感じがします。

Kerasの環境構築2

先程とは別の枠組みでKerasのライブラリをインポートして記述することも可能です。
import文が簡単に書ける以外でどう違うのかは今のところわかっていません…

それにはまずKerasパッケージを入れる必要があるので,パッケージインストールの例に習って,
ossyaritoori.hatenablog.com
1.パッケージを探すために以下のコマンドを叩きます。

anaconda search -t conda keras

2.出てきた候補の中でwin64に対応していて,なるべく新しそうなものをチョイスします。2017年5月末ではconda-forgeが良さそうです。
そして以下のコマンドを叩きます。

anaconda show conda-forge/keras

3.最後に2で示されたURLをコピって貼っておしまいです。

 conda install --channel https://conda.anaconda.org/conda-forge keras

Kerasを用いた手書き文字認識 テストコード1

Tensorflowにもとから入っているKerasを用いて実行します。

コード例1

こちらのブログのコードを転用しています。
書き方が公式とちょっと違う気がしているので戸惑うかもしれません。

qiita.com


結果

以下,10000回学習した結果です。
テストの結果認識率は約97%で前回の場合よりも大分改善しました。

Training...
  step, accurary =      0:  0.025
  step, accurary =   1000:  0.910
  step, accurary =   2000:  0.935
  step, accurary =   3000:  0.955
  step, accurary =   4000:  0.940
  step, accurary =   5000:  0.970
  step, accurary =   6000:  0.985
  step, accurary =   7000:  0.965
  step, accurary =   8000:  0.970
  step, accurary =   9000:  0.975
  step, accurary =  10000:  0.980
Test accuracy: 0.9727

考察?

前回のパーセプトロンからの変化として,
多分ノード数と活性化関数が変更になったこと,活性化関数が各層にかかったことがあります。
あとドロップアウトというノードの一部をランダムに無視する手法も用いています,

関連して,学習にかかる時間も精度も大幅に上昇しました。

ドロップアウトの影響

例えばドロップドロップをなくすと次のような結果になります。
あれ?そんな変わらない?ただ,それまでの経過を見るにそれなりには差があるようです。

Training...
  step, accurary =      0:  0.155
  step, accurary =   1000:  0.935
  step, accurary =   2000:  0.915
  step, accurary =   3000:  0.950
  step, accurary =   4000:  0.955
  step, accurary =   5000:  0.945
  step, accurary =   6000:  0.960
  step, accurary =   7000:  0.955
  step, accurary =   8000:  0.970
  step, accurary =   9000:  0.955
  step, accurary =  10000:  0.965
Test accuracy: 0.9726

Kerasを用いた手書き文字認識 テストコード2

Kerasの使用法に関しては公式のDocumentがわかりやすいのでこれを見てください。
Sequentialモデルのガイド - Keras Documentation

tensorflowに組み込まれているKerasライブラリも基本的にこれらと同じ書き方が出来るようですね。

Kerasでのモデルの記述の仕方

非常に直感的な書き方になっていてmodel.addで層を加えていきます。
最初のSequencial()は言わばInitializationで
その後.addで層を入力側から見て加えています。Dence(A,input_shape=B)というのは入力の自由度がBで出力自由度がAということです。

従って入力層と隠れ層は512のノードを格納した配列ということになります。(よね?)
その後Activationで活性化関数を指定しています。前回はシグモイドでしたが,近年の深層学習ではReLu関数が主流のようです(文献1)。

# build model
model = Sequential()
model.add(Dense(512, input_shape=(784, )))
model.add(Activation('relu'))
model.add(Dropout(0.2))
model.add(Dense(512))
model.add(Activation('relu'))
model.add(Dropout(0.2))
model.add(Dense(10))
model.add(Activation('softmax'))

model.summary()

テストコード

先程のブログを参照するとこうなります。


実行の様子

正直結果はそんなに変わらないので,こちらはSpyderの表示を見せます。
f:id:ossyaritoori:20170531200353p:plain

これをずっとやった結果:Test accuracy: 0.9837とやはり98%近い性能を出せました。


今後やってみたいこと

これは結局テストデータを使っているだけなので実際にこの学習器をOpenCV等と連携して
実画像の認識をやってみたいなぁと思います。
思っているだけかもしれませんが。

Tensorflowを用いた手書き画像認識:MNISTを使ったテストコード(Windows,Anaconda,Python3.5)

記事の依存関係

以下の記事を元に環境などについては辿ってください。
ossyaritoori.hatenablog.com

Windows10でAnacondaに仮想環境を敷いた上で行っています。
Python3.5で行っておりCPUVersionです。

コードはJupyter notebookで記述しております。

MNISTについて

MNISTは0~9の手書き文字画像を7万枚集めたデータセットです。
これは標準のデータライブラリとして公開されているのでこれを用いて文字認識をしたいと思います。

以下公式?の説明の翻訳があります。
TensorFlow : ML 初心者向けの MNIST (コード解説) – TensorFlow
f:id:ossyaritoori:20170529020341p:plain

使用した学習モデルについて

いずれはディープラーニングとかに移行したいですが,今回は28×28の画像入力を単純に並列な入力として扱ったロジスティック回帰を行います。

  • 入力層 768ノード
  • 隠れ層 100ノード
  • 出力層 10ノード

としました。

バイアスを加えた線形和に対して,活性化関数としてシグモイド曲線を用いています。

また,最終的なOutputはsoftmax関数で定義するものとします。
誤差関数にはクロスエントロピーを使っています。
一般的な分類問題に用いられる形です。

参照したサイト

正直今回のコードは以下のスライドを流用しています。

www.slideshare.net

参考元との差異

上記のスライドの後半のコードを真似ていますが,Verが違うことに依る関数の違い等があります。

  • Python2系と3系の違いによるPrint関数の変化。
  • Softmax関数のCrossEntropyの記述方法が変わったことの反映

fix the error when using tensorflow 1.0 by xinlinli1990 · Pull Request #15 · udacity/CarND-LeNet-Lab · GitHub

コード

例のごとくGISTで貼っておきます。
行毎にコピペして1つの.pyファイルに置いてもいいですし,
自分のnotebookに貼って試してみるのもいいでしょう。

学習の実行結果

学習に伴い,誤差関数が減少しているのがわかります。
なお,確率的再急降下はランダムなので急に上がったりします。
今回はよくできた方ですね。

WARNING:tensorflow:From <ipython-input-32-fa591c7fbded>:3: initialize_all_variables (from tensorflow.python.ops.variables) is deprecated and will be removed after 2017-03-02.
Instructions for updating:
Use `tf.global_variables_initializer` instead.
step = 1000, loss=2.13
step = 2000, loss=1.45
step = 3000, loss=0.96
step = 4000, loss=1.22
step = 5000, loss=0.82
step = 6000, loss=0.89
step = 7000, loss=0.80
step = 8000, loss=0.67
step = 9000, loss=0.59
step = 10000, loss=0.38

警告について

なんか警告が出ていますがどうやらinitialize_all_variablesというのは今後使うなということみたいです。
TensorFlowのinitialize_all_variablesがDeprecatedになった件 - Qiita

代わりに以下のglobal~~を使えとのことです。 verが古いtensorflowでは実装されていないらしいので注意!

tf.Session().run(tf.global_variables_initializer())

結果

さて,訓練用データで訓練した結果をTestデータで検証した結果は以下のとおりです。

Accuracy (test data):   0.80%
True label: [7 2 1 0 4 1 4 9 5 9 0 6 9 0 1]
Est Label: [7 6 1 0 4 1 4 9 9 9 0 6 9 0 1]

やはり実用的にはちょっと低すぎますね。
層の構造を変えたりするとまた変わってきそうです。

Convolutional networkになるとどうなるんでしょうね。

エディタに関すること

jupyter notebook勧められて使いましたが結構良さげですね。
matlabでCtrl+Enterでセッションごとに実行するのとほぼ同じ感覚なので結構はかどります。

でもシャットダウンでCtrl+Cが上手くいかないのは仕様か何か?

関連書籍

Learning Tensorflow: A Guide to Building Deep Learning Systems

Learning Tensorflow: A Guide to Building Deep Learning Systems

Anacondaの仮想環境上でのパッケージ確認と追加の方法について

背景

Anacondaで仮想環境を作って満足していたら新しい環境に足りていないPackageがあったので
いろいろと入れる話になったというアレです。

1.仮想環境の立ち上げ
ossyaritoori.hatenablog.com

2.エディタのインストール(どうやらこの過程で結構いろいろはいったらしい。)
ossyaritoori.hatenablog.com

仮想環境にPackageを入れる。

2,の記事で合ったように外から
conda installを行うことでも入れることは可能みたいですが,以下のブログを参考にした手法でやってみます。
Anacondaの使い方 その2 (環境構築コマンド&ライブラリインストール) - Python (Windows) 備忘録

入っているPackageの確認

まずは使う仮想環境へactivateで入ってください。
その後,以下のコマンドを行うことで現在の環境を確認することが出来ます。

pip freeze

どうでしょう?僕の環境ではmatplotlibがありませんでした。

入っているPackageの確認2

失礼,anacondaを使っている場合は

conda list

を実行した方が良さそうですね。

特定のパッケージ(matplotlib)を入れる

anaconda search -t conda matplotlib

と入力すると候補がた~くさん出てきます。

そのうち下段の方にこんなのが出てきますね。
f:id:ossyaritoori:20170528225925p:plain
このうち,win-64ってあるのが64bit版に対応するパッケージです。
この名前,今回は「ukoete/matplotlib」をよく覚えて置きましょう。

次にこれを用いて以下を実行します。

anaconda show ukoethe/matplotlib

すると,最後の方に
「To install this package with conda run:
conda install --channel https://conda.anaconda.org/ukoethe matplotlib」
と出ます。
なるほど。

最後にこのURLを用いてinstallとすることで完了です。

conda install --channel https://conda.anaconda.org/ukoethe matplotlib

最終的にnumpyとかも一緒に入れてくれました。

少し手間がめんどくさそうですが,
OS環境に対応したモジュールを入れられるので環境依存に謎エラーに苦しめられないための布石ってことですね。
手間を省くための手間を惜しまない精神,大事です。

疑問

結果をconda listで見た所,numpyが被ってるんですけどこれって大丈夫なのかな?

numpy                     1.12.1                   py35_0
numpy                     1.12.1                    <pip>

Python Anacondaの仮想環境上での開発環境

前の記事で仮想環境を立てましたが,エディタをデスクトップから起動するとメインの環境で立ち上がるという問題があります。

Spyderを仮想環境上で呼ぶ。

Matlabコンソールぽくてとりあえず気に入ったspyderについて。

spyderを仮想環境上にインストー

仮想環境名は前回を引き継いで「tf35」とします。

conda install -n tf35 spyder

仮想環境から呼び出し

activate tf35

とした後に

spyder

と打つだけでした。楽ちんですね。

Jupyterの場合

正直はじめてまともに起動します。

インストー

同じ!!

ひょっとしたらいらないのかも?

起動

activate後に

jupyter notebook

とうって起動。

使い方はまた後ほど。

Windows上でTensorflow/Opencvの環境構築(Anaconda使用)

むかぁしTensorflowをUbuntuに入れてたことが合ったのですが引っ越しの際に全て消し飛ばしてしまったのでしばらく放置していました。
気がついたらWindowsでもTensorflowを出来るということなのでやってみました。

Anaconda で Python環境構築

これは既にやっているものとします。
ossyaritoori.hatenablog.com

そういやTwitterでJupyterを使おうと言われたので使用感を試しているところです。

Anaconda でTensorflowの環境構築(CPU版)

Anacondaって使う環境を分けることが出来るんですね。
上手く言えないけど開発毎にパッケージ群を分離して選択できるというかなんというか。

環境の構築

んで,今回は「tf35」と名前をつけた環境を作ります。

以下のように打ってください。

conda create -n tf35 python=3.5

これでtf35という名前の独立した環境が立ち上がります。

Anacondaを介してインストールする際の罠として「TensorflowはPython3.5しかサポートしていない」というのがあります。

Anacondaで最新版をインストールすると3.6系になるので私はこれでハマりました。
「No matching distribution found for tensorflow」ってエラーを見かけたらこれかもって思ってください。

したがって,後ろについている「python=3.5」とすることによってこの環境は3.5系を基準に動かすことが出来るようにセットアップされます。

アクティベーション

作った「tf35」という環境をactivateするには

activate tf35

終了する際には

deactivate

としてください。

Tensorflowのダウンロード

以下の公式?の通りにコマンドを打って最新版を手に入れてください(2017/5/25現在)
Installing TensorFlow on Windows  |  TensorFlow

pip install --ignore-installed --upgrade https://storage.googleapis.com/tensorflow/windows/cpu/tensorflow-1.1.0-cp35-cp35m-win_amd64.whl

アクティベーション結果のチェック

正直変なエラー出たら全部消してやり直すかStackflowみてください。

 import tensorflow as tf
 hello = tf.constant('Hello, TensorFlow!')
 sess = tf.Session()
 print(sess.run(hello))

これで何もエラーが出なかったらOKです。
もう一度付けるときはくれぐれもactivateを忘れずに。

そういやTensorflowの英語版の教科書もあったんですね。
誰か勝手送ってくれ~(お金ない)

Learning Tensorflow: A Guide to Building Deep Learning Systems

Learning Tensorflow: A Guide to Building Deep Learning Systems


次は仮想環境上でのエディタ環境について。

2017年9月追記:anaconda 標準環境のセットアップ

どうも新しい環境(condaprompt)で試した所、いろいろとパッケージが入っていない現象にぶち当たりました。
以下のコマンドでPython3.5のanaconda標準環境をダウンロードできます。

conda install anaconda python=3.5

なお、いくつかのパッケージはダウングレードされるようなのですがまぁ問題なさそうではあります。

おまけ

折角tensorflowを入れるのでOpencvもついでに入れようと思います。
先程作ったtf35の環境上で

anaconda search -t conda opencv

としてopencvディレクトリを探します。

ver228/opencv というところが3.2のwindows64bit版対応を公開しているようなので

anaconda show ver228/opencv3

として出てきたURLからダウンロードします。

conda install --channel https://conda.anaconda.org/ver228 opencv3

はい。pythonを起動して以下のように確認できたらOKです。(>>>はコマンドではない)

>>> import cv2
>>> cv2.__version__
'3.2.0-dev'