C×Labo

主にプログラミング関係について書いていきます。

深層学習TOP

記事へ飛ぶには見出しをクリックしてください。

ニューラルネットワークの仕組み

ニューラルネットワークの仕組み
・活性化関数
・学習とは?
・誤差関数

確率的勾配降下法(SGD)

・勾配とは?
・勾配降下法とは?
確率的勾配降下法SGD
・ミニバッチ
・テストデータ
過学習の緩和
・学習時の小技

誤差逆伝播法

誤差逆伝播法とは?
・順伝播と逆伝播の違い
・勾配消失問題

誤差逆伝播法

_________________________________________________________________________________________
【目次】

_________________________________________________________________________________________

誤差逆伝播法とは?

深層学習で使われる学習のアルゴリズム
学習データと多層パーセプトロンの出力が一致するように各層の間の結合荷重を
修正するという学習法。

順伝播と逆伝播の違い

順伝播は非線形計算であるのに対し、
逆伝播は線形計算である。

勾配消失問題

ニューラルネットワークの層が深くなるにつれて、学習する際に勾配が0に
近くなり、浅い層で誤差が消失する問題のこと。
これの回避方法は自己符号化器についての記事に書きます。

確率的勾配降下法(SGD)

_________________________________________________________________________________________
【目次】

_________________________________________________________________________________________

勾配とは?

 ベクトルです!!!!
数式は省きますが∇Eは勾配だと思ってください。

勾配降下法とは?

勾配降下法とは現在の重みwを負の勾配方向に少し動かし、これを何度も繰り返す方法。
現在の重みをw^{(t)}、動かした後の重みをw^{(t+1)}とすると、

w^{(t+1)}=w^{(t)}-ε∇E

εとは、学習係数と呼ばれ、
wの更新量の大きさえお定める定数である。
この式を繰り返せば極小値に到達できる。

しかしε(学習係数)は小さすぎると学習にかかる時間が大きくなり、
大きすぎると場合によってはwが増大してしまうこともあるため、
このε(学習係数)の決定はかなり重要な問題の一つになっている。

確率的勾配降下法SGD

先ほど説明した勾配を使ったwの更新をバッチ学習と呼ぶ。
これに対し、データの一部だけを使ってパラメータを更新する方法があり、
これを確率的勾配降下法と呼ぶ。
これのメリットは訓練データの冗長性がある場合、学習が速く実行されることである。
他にもメリットは多くある。

ミニバッチ

重みの更新を少数のデータの集合をひとまとめにし、その集合単位で重みを更新する。
このひとまとめにした集合をミニバッチという。
このミニバッチは10~100前後にすることが多いそうだ。
あまり大きくするのも良くない。
クラス数が10~100程度で、かつ各クラスの出現頻度が等しい場合は、
分類すべきクラス数と同サイズのミニバッチを作ると良いらしい。

テストデータ

前回の記事にも少し登場したテストデータ。
これは訓練データで学習したものをテストするためのデータという
説明であった。訓練データでのaccuracy(精度)が高くても汎用性がないので
あまり意味がない。
テストデータでaccuracyが高くなればそれは汎用性があり、使えるということである。
訓練データでの誤差とテストデータでの誤差が乖離した状態を過学習という。
いかに過学習することなく、テスト誤差を小さくできるかが鍵である。

過学習の緩和

過学習はネットワークの自由度が高ければ高いほど起きる可能性が大きくなる。
しかし、だからといって自由度を減らすことは基本的にはあまり望ましくない。
そこで正則化という方法があり、2つ紹介する。(数式を使わずに説明します)

  • 重みの制約

重み減衰:誤差関数に近江の二乗和(二乗ノルム)を加算し、最小化すること。
正則化の強さを制御するパラメータがあり、その値は0.01~0.00001の範囲から選ぶ。
これにより、学習時に小さい重みが選好されることになる。

重み上限:重みの上限を制約する方法。
各ユニットの入力側結合の重みの二乗和の上限を制約する。
この方法と次に出るドロップアウトを組み合わせると高い効果が得られるそう。

多層ネットワークのユニットを確率的に選別して学習させる方法。
中間層の各層と入力層のユニットを決まった割合(0~1.0)で選出し、
それらを無効化する。
よく使われている方法である。

学習時の小技

学習時に実行すると性能が向上し、学習速く進められる方法がいくつかあり、その方法を紹介する。

  • データの正規化

データに偏りがある場合、偏りをなくす処理を行う。
データの標準化とも言う(?)らしい。
数式はよくわからないので、コードで書くと以下のような感じにする(python)

data -= np.min(np.abs(data))
data /= np.max(np.abs(data))

統計学を勉強していないので、詳しいことは分からないが、
こう書くと偏りがなく、正規化できるらしい。(違っていたらごめんなさい)
近いうちに統計学も勉強します・・

  • データ拡張

手持ちのデータになんらかの加工を施して、水増しする方法。
画像データの場合、画像を平行移動したり、左右に鏡像反転したり、
色を若干変えたりしたデータを追加する。
画像以外の時系列の数値的なデータは水増しはできるのだろうか?
加工のしようが無い気がしたのでできないと思ったが、
できるのであれば教えて欲しい・・・

  • 複数ネットの平均

複数の異なるニューラルネットを組み合わせると精度向上につながる。
パラメータの異なった複数の訓練データや、「データ拡張」で書いた加工をしたデータを用いて、
複数の出力を出し、その平均を出す。
この平均のことをモデル平均と呼ぶ。
ドロップアウトは単一のネットワークを使って、実質的に複数のネットワークのモデル平均を
実行する効果があると考えられている。

  • 学習係数の決め方

学習係数は自動で決定させる方法もあるが、現在は手動で試行錯誤的に決定するのが
良いと言われている。
ここではその方法を紹介する。

  1. 学習の初期ほど大きな学習係数を与え、進捗とともに小さくしていく。
  2. ネットワークのすべての層に同じ学習係数を用いるのではなく、層ごとに異なる値を使う。その際、各層の重みの更新速度がなるべく揃うように設定するのが良いと言われている。

学習係数を自動で決定(変化)させる方法では、AdaGradが最もよく使われているらしい。
(多分現在ではAdamのほうが人気)

順伝播型ネットワーク(多層パーセプトロン)

__________________________________________________________________________
【目次】

__________________________________________________________________________

ニューラルネットワークの仕組み


ニューラルネットワークでよく見るこの図
f:id:c-laboratory:20170506010036j:plain


u=x_1w_1+x_2w_2+x_3w_3+x_4w_4+b

ニューラルネットワークは、
入力層のユニット(x)に重み(w)を掛けバイアス(b)を足して新たなユニット(u
を作ること!(?)

この新たなユニットっていうのは深層学習(ディープラーニング)でいう中間層の一つになるんだと思う。

ニューラルネットワークを複雑化したがディープラーニングっていう認識

f:id:c-laboratory:20170506002425j:plain

数式で書くとこうなるらしい。

{ \displaystyle
u_j = \sum_{i=0}^{I} w_{ji} x_i + b_j
}
z_j = f(u_j)



このくらいの数式ならなんとかまだ分かるが、機械学習に出て来る数式は、
基本理解できていない・・

二つ目の式のz_j = f(u_j)は何かというと、
活性化関数を適用したものの出力である。

活性化関数

活性化関数とは、ニューラルネットワークにおいて線形変換をした後に適用する非線形関数もしくは恒等関数のこと。

ん?難しい。
私は、上述した数式の出力値(ここでいうz)を決めるものだと覚えた。

活性化関数は様々な種類があるが、ここでは以下の3つの特徴を書いていく。

 入力の絶対値が大きな値をとると出力が飽和し、一定値になり、その間の入力に対して出力が徐々にかつ滑らかに変化。

  • ソフトマックス関数{ \displaystyle z_k= \frac {exp(u_k)}{\sum_{j=0}^{K} exp(u_j)}} (出力のk番目のユニットの出力の場合)

 他の活性化関数の場合、ユニットkの値の出力z_kは、同ユニットへの総入力u_kのみから決定されるのに対し、この関数ではこの層の全ユニットへの総入力によって決まるという特徴がある。

  • ReLU関数(ランプ関数)f(u)=max(u,0)

 計算量が小さく、学習が速く進み、よい結果が得られることで主流の関数。
入力が0を超えていたらそのまま出力、0以下なら0を出力。

学習とは?

 機械学習では、訓練データとテストデータという言葉がよく出る。
訓練データとは、ある数値等を入力したときに望ましい出力(正解のデータ)にするためのデータであり、
テストデータは訓練データで学習した内容と試すデータである。
では、ここでいう学習とは何か?
訓練データは、1つの入力に対して望ましい出力があり、パラメータ(今回の場合はw)を変えることによってこの望ましい出力に近づけるようにする。このパラメータを調整することを学習と呼んでいる。

誤差関数

訓練データと、正解のデータに近づけるためのコンピュータが内部で計算している関数との近さをどのように測るか、その尺度が大切である。この尺度のことを誤差関数と呼ぶ。

今回2つの誤差関数を簡単に簡単に紹介する。(数式を知りたい人はごめんなさい)

  • 二乗誤差

 主に回帰問題で使われる(らしい)。

 主に多クラス分類で使われる(らしい)。

以上。
数式の詳しい説明は私ができないので書籍等を参考にしてください。

 二値分類と他クラス分類を別で書いているところもありますが、
二値分類のものを他クラス分類の書き方で書いても得られる結果は同じだそう。

 ソフトマックス関数を出力層の活性化関数で使用すると、
学習の進み具合が著しく遅くなる等があるため、
通常は重み減衰やこの層のユニットを適当に1つ選び、
そのユニットへの入力を強制的に0にする方法をとると良いそうだ。