mocamocablog

tech blogがメインです

覚書メモ 情報学関連書籍ベストセラー1位:「詳解 ディープラーニング 」の著者・巣籠主催勉強会

先日の水曜日に詳解ディープラーニングの勉強会があったので大手町にあったので行ってきた

connpass.com

会場は小さいオフィスだったので募集人数も10人満たないくらい。
以下お話をしてた内容を箇条書きで記載

巣籠さんについて自己紹介
東大で教えてたりしてるらしい。

最初はディープラーニングの話題になるまでの歴史を簡単に説明
2012年から海外でビックイベントがあり
ディープラーニングが話題になったとかの歴史背景などの話
そのイベントでyoutubeの画像データから猫が認識できるようになったことでざわざわしていたとか

その頃、日本での話題性はごくわずかで
その時に巣籠さんはディープラーニングが面白いと思って論文を読んでいたそうです。
巣籠さん自身言語マニアだったのでPython以外でもいろんな言語で実装してる
詳しくはgithub参照

github.com

 

以下から詳解ディープラーニングのお話
詳解ディープラーニングがあれば書籍を見ながらがわかりやすいと思います。
主に3章から5章までを解説
聞きながら記録してるため途中抜けたり、誤った記載がある可能性があることご了承下さい。

 

1章数学、2章Pythonなので割愛

ニューラルネットワークとは
いくつかある人工知能分野におけるアルゴリズの一つ

ニューロン画像とは
電気信号で人間は信号で脳を走らせている
脳とニューロンの仕組みは丸と矢印になる矢印が電気信号となる
結合の強さによって次のニューロンに伝わる電気量は変わる


あるニューロンが2つのニューロンから電気信号を受け取る
2つのニューロンのどちらかからどれくらい電気信号を受け取るか
ニューロンの発火式が重要
どんなにニューロンの発火式を複雑にしても根底は同じ

ステップ関数に変換すると脳仕組みがわかる 
それが脳の仕組みだから
複雑なのでベクトルを導入するが、以外と単純だよってこと

面倒なので単純パーセプトロンのモデルとなってる
アプリケーションの問題、ステップ関数の問題がある
例として迷惑メールが受信に入ってしまうのは我慢は出来るが
迷惑でないものが見逃しで出てしまうことがある。

そのためにシグモイド関数を利用
シグモイドであれば0から1値での範囲で確率で行える
補足としてステップ関数は0か1の値しかとらないため。

シグモイド関数になったものがロジスティック回帰
ウィキで調べると別のアプローチがある。
突き詰めるとニューラルネトワークで
fが活性化関数

ニューロンからどのくらいで受け取るか 重み
当地はどれくらいにするか バイアス


ネットワークの学習
ニューラルネトワークの大前提として
どんな複雑なモデルも目指すのはモデルの予測値と10歳の値との誤差を0に近づける

ロジスティック回帰だとシグモイド関数ニューロンの発火率

モデルの予測値を綺麗に表したいので特殊な気表になってる
それをひとまとめにする

式を一つにすると何が嬉しいか?
・関数の最大化問題に書き換えができる
・入力データに対して最大化する

 

最大推定するようにパラメータを調整できればうまくニューラルネットワークの学習ができている

 

関数の最大と最小といえば微分

パラメータは重みとバイアスなのでそれぞれ偏微分をすればいい

 

交差エントロピー関数
大事なのはモデルの予測値と正解値との誤差を評価するために誤差関数を定義
誤差関数を最小カスベク偏微分を0になるパラメーター値を目指す

偏微分して0になるパラメータを求めればいいが解析的に求めるのは不可能
反復学習でアプローチする

微分値が0だった場合
値が更新されなくなったら勾配が0になる値を求める手法である


まとめ
モデルの予測値と正解値との誤差を評価するために誤差関数を定義
などなど


実装の流れについて解説 注意:TensorFlowだけ解説
1:変数を定義
2:式を定義
3:セッションを定義 importみたいなの
4:式を評価

大きく変数は2つのvaiable:実際の値を持った変数

placeholder:データ用で実際の値を入れるもの
線形代数:元の式をそのままで使えないplaceholderに導入してから式を入れる

誤差関数も実装通りできる
勾配降下法は微分式を求めなければいけなかったがTensorFlowが出てきたので
微分をしなくてもよくなっている
式を書くだけでよくて微分計算をする必要なし

 

XORゲート
どっちも同じ値であれば発火しない
ロジスティック回帰では分離できない
それを解決するために多層パーセプトロン
層が増えても考えてることは同じ

とにかく予測値と誤差も0に近づける点は共通

 

誤差逆電場法
出力層における誤差をネットワークを遡って全体に反映させる
ここでも誤差を0に近づけるのは同じ


誤差逆電場法と確立公開勾配法

プロビット回帰 累積分布関数
シグモイド関数が確率になると説明した
例えば正規分布の確率分布がシグモイドぽいラインになる

TensorFlow使うときは問題ないがシグモイド関数微分について何か言ってましたが忘れました


4章
ディープラーニングは関数の合成とは層がいくつもあるところ
層が深いと複雑な関数の表現が可能だが、複雑にすればいいものでもない

テーラー展開すると多項式で考えると?
一次関数で考えたり三角関数で近似してみるなど

4次関数で定義したり良くなるか
16次関数に無理より近似するとウニョウニョしてoverfittingを起こす
データを全て通るようにしていることです。

 

真のパターンを近似させるため
何も工夫をしないと学習がうまくできない場合あり

・勾配消失問題

層が深くなると誤差逆伝播法がうまくいかなくなる
シグモイド関数微分の最大値:0.25

代わりにシグモイドではなくハイボリクタンジェントに置き換える
ハイボリクタンジェント微分すると最大値は1.0
勾配消失しにくい

ReLU(レル)、Leaky ReLUとか
勾配消失問題は活性化関数で解決


ドロップアウトはなんで有効なのか
学習の際にランダムにニューロンドロップアウト(除外)させる

 

アンサンブル学習
学習全体ではパラメーターの値が調整される

オーバーフィッティング問題 
ドロップアウトで解決させる
学習を途中で打ち切る
オーバーフィッティングを防ぐフリーランチというのがある

 

以下について説明あり

データの正規化
重みの初期化
学習の設定


・データの正規化
データの分布を整える平均を0にする処理を行うのが効率的
データの正規化により重み成分は政府の値を持つはず

データの偏りがなければ政府の成分は半々に近づくはず重み成分は0で初期化するのが良いが、そうはいかない

すべての同じ値で初期化してしまうと誤差逆電波法の際に勾配の値も同じになってしまう
重みの値が更新されない

 

0に小さい乱数rで初期化することで問題を回避
正規分布が理想
平均と標準偏差で表す


標準偏差はあくまで1の標準正規分布を適切な係数を掛け合わせて
うまく初期値を生成できないか

 

どうするかというと
理想的な分布を作るにはユニット数が大きいほど
生成される値にばらつきが出やすくなってしまう

 

入力データが正規化されてると  E [xi]=0
重みが理想的な分布をしているとE[w ji]=0

 

分散が同じようなもので伝わる
n回学習で係数があると余計となる
1/nで設定して初期化すると学習がしやすくなる

 

勾配降下方のαの係数は大事
これが大きいと収束しない場合があるが、小さくしても問題あり
山を越えられず局所最適解に陥りやすく、収束までに時間がかかる
なのではじめは大きく徐々に小さくしたい

 

よく使われるのはモメンタム モメンタム項がよく使われる

adagradなどいろいろある
adamとかもあるよとのこと

 

BatchNormalizetionを適用すれば問題なし
事前にデータセットを正規化するのではなくミニバッチ単位で正規化
事前に正規化しrてもネットワーク内部で分布
BatchNormalizetionは活性化関数の一つみたいなもの

ミニバッチをの平均および分散を用いてデータを変換
微分計算ができるよという解説

 

特徴
バッチ内で正規化するためバイアス項が不要
学習率を大きくしても学習がうまく行く
ドロップアウトを用いなくても般化性能が高い

adam batch normalizationなど入れれば完璧

ディープラーニングが話題になったのは合成関数が出てきたため


リカレントニューラルネットワークについては画像での畳み込みが有名
今後どうなるか不明? 不要?

 

時系列データを扱うためのモデルについて
時間を考慮して取り入れる必要がある
画像分野に注いで研究が活発で、特に自然言語処理の音声処理とか


処理の流れは隠れ層が追加されただけで出力はいつも通り
過去の隠れ層が追加されてもアプローチ自体は変わらないが、過去の逆伝播も考える必要がある

 

・RNNにおける更新式
理論的にどこまでも過去に遡れるが計算上限界がある
30くらいが限界らしい

 

・simpleRNNの問題点
長期の時間依存性は学習できない

理由は勾配が消失してしまう
そのためLSTMの登場

 

LSTMはよく使われる ニューロンからブロックへ
時系列データ処理における基本

隠れ層のLSTMブロック毎が入力層にあるニューロンに当たる
CEC出力ゲートの説明あり

 

・勾配消失問題の原因
通常のニューラルネットワーク同様

活性化関数の微分が係数としてかかる
DNNでは幾つかのテクニックを積み上げた

 

・誤差の定常化 
CECで止まらせる存在となってる 
それが最初の段階でさらに誤差を止まらせるニューロンがあり
これでCECで勾配消失問題は解決した

 

・入力重み衝突
自身が発火すべき信号が伝播されてきた時は重みを大きく活性化するべき
無関係な信号が伝播された時は重みを小さくし非活性化のままであるべき

上記2点は両者はお互いに打ち消しあう関係にある

出力に関しても同様


・出力重み衝突

依存性のある信号を
受け取った時”のみ”活性化する必要がある
必要になったタイミングのみ信号を伝播


入力ゲーと 出力ゲート
入力ゲートはシグモイド関数
時間軸で関係する時は開けて不要であれば閉じる
入力と出力ゲートがあるので衝突の問題が解決される
時系列のやつはこれでいける

 


・忘却ゲートの導入
上記で十分と思われてたが劇的にパターンが変化する時系列データをうまく学習ができない問題が発生
必要なくなったタイミングで過去の情報を忘れ去ることも同様に重要
それを対応するのが忘却ゲート
シグモイド関数を使用
モデルの式はアップデートされるが大したものではない
KerasのLSTMはsecondが実装されてる

TensorFlowはセカンドまで実装されてる
サードは覗き穴結合


もし出力ゲートがずっと閉じてる場合
CECの状態を外部から知ることができない

CEC状態から他のゲートから見えるようにする値を見れるようにしておきたいから
誤差の値が出力ゲートに影響を与える
これでLSTMブロックがなくてもいいとのこと

 

GRUは割愛して終了