ろこらぼ

僕の開発の手順とか実験結果とか感想とかをつらつら書き込んでいくお墓.僕の魂を成仏させるためのお墓です.いいね・ブクマ・コメント待ってます

TensorFlow-勾配法でもはや機械学習(1)-

どうも皆さんこんにちは.今日はもはや機械学習です.大事なことなので二回言います機械学習です.

今回から,matplotlibというものを使っていきます.あとnumpyとkeras.もし,入っていない場合は,コマンドラインで

pip install matplotlib
pip install numpy
pip install keras

をすればインストールできるので,よろしくお願いします.

TensorFlow使ったことない人は,
www.nekorokomemordm.info

そもそも導入していない人は,
www.nekorokomemordm.info

以上,よろしくお願いします.

勾配法って?

ググれ.
冗談です.

そもそも機械学習って?

機械学習とは,予測するためのパラメータの調整をすることが目的なんですよね.
イメージとしては,スーパーの駐車場に自転車が100台あるよりも,車が100台あるほうが店内には人が多そうじゃないですか.
これは,自転車だとおひとり様が多くて,車だと,ひとり以上乗れますから,自然とバイアスがかかるんですよね.
f:id:ryuga13tk:20190121223228p:plain
この場合だと,自転車の台数≒人数と考えられますが,車だと,乗っている人数を実数kとすると,k×車の台数≒人数っていう風に推定できるからです.

今回の場合,自転車には原則ひとりで乗ってもらって,,,自動車に乗っている人は1~5人としましょう.そうすると,自転車の数をa,自動車の数をbとして,実際に店内にいる人をyとして,車に乗っている人を実数k人と表現とすると,その関係は,
a + bk = y
となります.
これはただの1次関数ですが,このkを予測するのに,機械学習を使います.実際はもっと複雑なモデルに使いますが,イメージのための簡略化です(あんまりにも分かりにくいと判断したらそのうちかえます).

んで勾配法って?

じゃあ勾配法っていうのは何かっていう説明をするのに,実は1次関数じゃ無理なので2次関数(x-1)^2で考えていきます.
勾配法とは,その関数において,最小もしくは最大となるxを探すためのアルゴリズムになっています.
(x-1)^2について,TensorFlowで書いていきます.

%matplotlib inline
import numpy as np
import tensorflow as tf
import matplotlib.pyplot as plt

x = tf.Variable(2., name = 'x')
func = ((x - 1) ** 2)

#以下4行グラフの描写のためのデータ.勾配法には無関係.
train_x = []
y = []
func_x = np.linspace(-0, 1.2, 200)
func_y = (func_x - 1) ** 2

# 勾配法のパラメータ更新担当.learning_rateの大きさで更新値が変わる.
optimizer = tf.train.GradientDescentOptimizer(
    learning_rate = 0.1
)

# パラメータを実際にずらしていく担当.sess.run(train_step)で実際にずらす
train_step = optimizer.minimize(func)

with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    
    for i in range(50):
        #更新.
        sess.run(train_step)
        #実行ごとに,更新された値を取得.
        train_x.append(sess.run(x))
        #更新したときのyの値を取得.
        y.append((train_x[i] - 1) ** 2)
    
    print(train_x)
    #更新の様子を描画.
    plt.scatter(train_x, y)
    #最小値を推定するグラフの描画.
    plt.plot(func_x, func_y)
    plt.show() 

ちなみにこれの実行結果は,
f:id:ryuga13tk:20190121225601p:plain
という感じ.
見事最小値を見つけ出しています.
ちなみに勾配法は実装しません,TensorFlowが用意してくれてるので.素晴らしい.

x = tf.Variable(2., name = 'x')

これに関しては,「2.」となっているのは,勾配法は初期値を決めてそこから最小値を推定するアルゴリズムなので,初期値が必要.
今回の場合はパッと見ただけで,最小値がわかるのでありがたみを感じないが,これが例えば,x^5 + 4x^2 + 1とかだと勾配法が強い.ただし,初期値を間違えると無限大に大きく(小さく)なる可能性がある...

勾配法のアルゴリズム

ここで,勾配法のアルゴリズムをちょろっと紹介.
勾配法(今回使用したのは最急降下法)は,最適化手法です.ニュートン法と似てる.

プログラム中の登場したlearning_rateをαと定義.初期値を推定する関数をf(x),初期値をx_0,更新後の値をxと置くと,更新後のxは,
x = x_0 - α*f'(x_0) (ちなみにニュートン法だとx = x_0 - f'(x_0))
と,なる.
なので,f'(x) = 0となる地点に近づくほど,更新値(α*f'(x))が小さくなって行くのがわかる.
つまり,傾きが大きい時ほど大きく更新して,小さくなると,少しずつ更新する.しかもこれを学習計数αである程度いじれるという.

部屋の価格が機械学習で予測される.

Kerasのデータセットに,犯罪率とか部屋の数とかもろもろのデータと住宅価格があるけれど,これ以上は長くなるので,今回はここまでにします.
機械学習は次回からです.
機械学習で住宅価格を推定するモデルの学習ですが,更新したら下にリンク貼ります.

TensorFlowでセッションとSaverについて

この記事から少しずつ機械学習要素がぽつぽつと出てきます.
今日はSaverとTensorBoardについてです.
前回の記事で,tf.session()を使って計算の実行を行いました.
TensorFlowの使い方をまだ知らないって人は,前回の記事をご覧ください.

www.nekorokomemordm.info

それでは始めます.

\二本立て/



Saverって?

Saverは,複数のセッションで計算結果を使いまわすときに使います.
セッションが変わると,変数は元の値になってしまうので,せっかく計算した値が別のセッションでは使われないということが発生してしまいます.
それのためにSaverを使います.
機械学習で,モデルの学習時にも使います.
一度,下記コードを実行してみます.

import tensorflow as tf

a = tf.Variable(1, name = 'a')
b = tf.assign(a, a + 1)

with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    print("1:", sess.run(b))
    
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    print("2:", sess.run(b))

これの実行結果は.
1: 2
2: 2
ということになります.
では,セッションが変わったときに,どうするかというと,さっきのSaverです.Saver込みのプログラムを示しておきます.

import tensorflow as tf

a = tf.Variable(1, name = 'a')
b = tf.assign(a, a + 1)

saver = tf.train.Saver()
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    print("1:", sess.run(b))
    saver.save(sess, 'model/model.ckpt')
    
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    saver.restore(sess, save_path = 'model/model.ckpt')
    print("2:", sess.run(b))

これを実行すると,
1: 2
INFO:tensorflow:Restoring parameters from model/model.ckpt
2: 3
となります.
セッションが変わっても,値が初期化されずに済みました.
厳密にいうと,初期化されてますが,saver.saveで,モデルを保存して,saver.restoreで,モデルの読み込みをしています.

グラフの可視化

ここで言うグラフとは,データフローグラフのグラフのことです.
グラフの可視化には,TensorBoardを使います.初期装備です,追加のインストールはありません.
流れとしては,実行→サマリの書き出し→グラフの可視化
といった感じです.

早速プログラムです.

import tensorflow as tf

LOG_DIR = './logs'

a = tf.constant(1, name = 'a')
b = tf.constant(1, name = 'b')
c = a + b

graph = tf.get_default_graph()
with tf.summary.FileWriter(LOG_DIR) as write:
    write.add_graph(graph)

\こんなの覚えられないよ/
^^

これを実行すると,該当のディレクトリに"events.out....."みたいなファイルが保存されているはずです.

次にコマンドプロンプトを開いて,該当のディレクトリのひとつ前まで移動します.
Anacondaユーザーは[Open terminal]で新しく開きましょう.
そしたら,コマンドプロンプトで

>tensorboard --logdir=logs

を実行してください.
そうしたら,URLが出てきたと思うので,それにアクセスしてください.
ちなみに自分の場合は,出てきたURLだと,マシンによってはなぜかアクセスできませんでした.なので,http;//localhost:(出てきた番号)でアクセスしましょう.f:id:ryuga13tk:20190120164333p:plain

こんな感じで出てきます.

f:id:ryuga13tk:20190120163647p:plain

前回の記事にも登場しているのですが,aとbを足すんだなぁ・・・って感じのグラフですね.それ以外に言いようがありません.間違いない(確信).

現場で使える! TensorFlow開発入門 Kerasによる深層学習モデル構築手法 (AI & TECHNOLOGY)

現場で使える! TensorFlow開発入門 Kerasによる深層学習モデル構築手法 (AI & TECHNOLOGY)

TensorFlowの基礎的な使い方

今日もTensorFlowのお話です.

TensorFlow入ってないよって人は,
過去の記事を見てください.
www.nekorokomemordm.info


それではいきましょう.

TensorFlowの基礎って?

TensorFlowとは,データフローグラフという概念を取り入れています.データフローグラフが分かっている方は,飛ばしてもらって構いません.

下のソースコードを見てください.

import tensorflow as tf

a = tf.constant(1, name = 'a')
b = tf.constant(1, name = 'b')
c = a + b
with tf.Session() as sess:
    print(sess.run(c))

一目見るだけでも,1+1の計算をしてそうだなぁ...と思う人が多いと思いますが,実際に1+1の計算をしているのは,どの部分だと思いますか?

聞き方で大体察しが付くとは思いますが,

sess.run(c)

が,実際に計算を行っている部分です.
じゃあ,c=a+bは何なのか,気になると思いますが,これがデータフローグラフであります.
データフローグラフとは,「構築」と「実行」が別々に行われた処理のことです.

先に構築をしておくことで,並列・分散処理が可能になっています.

では,a=...b=...c=...の処理は何なんだと思う方がいると思います.下の図を見てください.
f:id:ryuga13tk:20190119183658p:plain

見ましたね?
この図のようなグラフを定義することが,a=...b=...c=...の処理です.

そして,このグラフを定義した後一気にsess.run(c)で,additionを実行します.

このように,「構築」と「実行」を分けています.



TensorFlowでの処理

「TensorFlowの基礎って?」という部分では,tf.constantを使いました.これは定数になっていまして,これからは変数も混ぜたコードになっていきます.

サクサク行きます.説明もないので.

変数とその代入
import tensorflow as tf
a = tf.Variable(1, name = 'a') #変数の宣言
b = tf.constant(1, name = 'b') #定数の宣言
c = tf.assign(a, a +b) #aにa+bの値を代入して,その値を返すと定義

with tf.Session() as sess:
    sess.run(tf.global_variables_initializer()) #すべての変数の初期化
    print("1回目:[c, a] = ", sess.run([c, a]))
    print("2回目:[c, a] = ", sess.run([c, a]))

上記コードを実行すると,
1回目:[c, a] = [2, 2]
2回目:[c, a] = [3, 3]
という結果が出るはずです.
これは,コメントでも説明しているままです.
ちなみに,a = a + bは無理なのか?という質問があるかなと思いますが,出来ますが,実行結果が2になり,その結果がaに代入されません.なので,更新するためにassignを使います.
また,tf.global_variables_initializer()は,すべての変数を初期化するための関数になっています.
変数の初期化にはほかにもtf.initialize_variablesがありますが,一括で初期化できる前者のほうが便利です.

プレースホルダー

プレースホルダーは,実行時に値を入れてあげることができる便利な箱です.
定数だと実行時に変更するのはできないし,変数もできません.なので,プレースホルダーを使います.

import tensorflow as tf

a = tf.placeholder(tf.int32, name = 'a')
b = tf.constant(1, name = 'b')
c = a + b

with tf.Session() as sess:
    print("a + b = ", sess.run(c, feed_dict = {a : 1}))

実行結果は,
a + b = 2
のようになるはずです.

以上が,スカラの計算です.
もちろん,機械学習のライブラリなので,名前の通り行列・・・いや,テンソル(多次元配列)の計算もできます.
ためしに・・・

import tensorflow as tf

a = tf.constant([1, 6], name = 'a')
b = tf.constant([2, 7], name = 'b')
c = a + b
with tf.Session() as sess:
    print(sess.run(c))

を実行してみればわかると思います.
結果は,[ 3 13]です.

これは,ベクトルの計算ですが.
行列の計算だと・・・

import tensorflow as tf

a = tf.constant([[1, 6], [2, 3]], name = 'a')
b = tf.constant([[2, 7], [4, 5]], name = 'b')
c = a + b
with tf.Session() as sess:
    print(sess.run(c))

結果:[[ 3 13]
   [ 6 8]]


指定の仕方を変えれば,placeholderでも...ほら,簡単に.

import tensorflow as tf

a = tf.placeholder((2, 2), tf.int32, name = 'a')
b = tf.constant([[2, 7], [4, 5]], name = 'b')
c = a + b

with tf.Session() as sess:
    print(sess.run(c, feed_dict = {a : [[1, 6], [2, 3]]}))

結果:[[ 3 13]
   [ 6 8]]


以上です.
次回は,実行した結果を別のセッションでも扱うためのSaverを扱います.

現場で使える! TensorFlow開発入門 Kerasによる深層学習モデル構築手法 (AI & TECHNOLOGY)

現場で使える! TensorFlow開発入門 Kerasによる深層学習モデル構築手法 (AI & TECHNOLOGY)

TensorFlowの導入について

f:id:ryuga13tk:20190118172339j:plain

TensorFlowとは,Googleが中心に開発している機械学習を行うためのライブラリです.

今日はそれの導入について書いておきます.

 

 

(追記)すでにTensorFlowが導入してある人はこの記事へ

 

www.nekorokomemordm.info

 

 

 

 

TensorFlowとは

TensorFlowとは,テンソル(多次元配列)の処理のフロー(流れ)を記述して,最後にまとめて実行することができるライブラリです.

 

具体的には,変数や定数などを宣言した後に,それらを用いて計算をすると宣言をします.そして,最後に計算を実行しろと命令を出すと,宣言したとおりに計算を行います.
最後に計算をするというのが特徴ですね.

これを用いて,深層学習をします.

まずは導入から.

 

 

導入(Windows)

 Windowsの場合は,Anacondaを使います.

www.anaconda.com

 

Anacondaは2019/01/18時点では,Python3.7を選びます.

インストールは特に書くことがないです.

 

次にGUIで仮想環境を構築します.

「Anaconda Navigator」を起動して,[Environments]→[Create]→[Create new environment]で,[Name]はすきにしてください.
[Packages]は[3.5]で,[Create]を押せばそのうちできます.

 

次に,右向きの▲を押して,[Open Terminal]をクリックします.

すると,コマンドプロンプトが起動するので,

CPU版のTensorFlowなら[pip install --upgrade tensorflow]

GPU版のTensorFlowなら[pip install --upgrade tensorflow-gpu]

でインストールができる.ただし,GPU版なら,CUDAとcuDNNが必要になるので,自分で調べてね.

次は,Jupyter Notebookとその他のライブラリをインストールします.

[conda install jupyter]

[conda install -c conda-forge opencv]

 

これで,Jupyterが動いて,PythonでTensorFlowがインポートできれば導入完了.

インポートはCPU,GPU関係なく,[import tensorflow as tf]

とかで.

 

ちなみに簡単な計算をさせてみたいなら,

import tensorflow as tf

a = tf.Variable(1, name = 'a')
b = tf.constant(1, name = 'b')
c = tf.assign(a, a + b)

with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    print(sess.run([c, a]))
    print(sess.run([c, a]))

 

 で動かせる.

 

導入(Ubuntu)

Ubuntu使ってる人は,やり方わかるだろうし,頑張って.

 

 

なんて冗談で,Ubuntuは基本的に流れが同じで,Pythonのバージョンを合わせて,TensorFlowをインストールして,必要ならJupyter Notebookをインストールすればすぐにできそう(やってない).

 

 

 

実際に動かしていくのはまた今度やっていきます.

現場で使える! TensorFlow開発入門 Kerasによる深層学習モデル構築手法 (AI & TECHNOLOGY)

現場で使える! TensorFlow開発入門 Kerasによる深層学習モデル構築手法 (AI & TECHNOLOGY)