音声認識メモ(Kaldi)その16(Backpropagation Dan's DNN(nnet2))

前回の続き。
Backpropagation(誤差逆伝播法)によるパラメータ更新の流れを追ってみる。

Softmaxの出力結果(確率)が以下のとおりであったとする(正解となるpdf-classのみ記載)。
f:id:ichou1:20180617090002p:plain
小数点第6位切り捨て

確率の逆数にweightを掛けたものを求める(今回、weightは全て「1」)。
f:id:ichou1:20180617090011p:plain
小数点第3位切り捨て

確率が低いものほど、値(=誤差)は大きくなる。

この値をもとに、前のコンポーネントの誤差を求めながらパラメータを更新していく。

Propagationによるフレームの遷移が以下のとおりであったとする。
(splice、FixedAffine(LDA変換)が終わった状態からスタート)
f:id:ichou1:20180617090554p:plain
<図の説明>
オレンジ色の丸がフレームのデータ部分を表す
" A x B"は、データの行数A、列数Bを表す("mini"はミニバッチサイズ、今回は「64」)
矢印が各コンポーネントを表す

誤差逆伝播(1)

まずは、「Softmax」コンポーネントから。

nnet2/nnet-component.cc
in_deriv->DiffSoftmaxPerRow(out_value, out_deriv);

f:id:ichou1:20180617092401p:plain
<図の説明>
緑色の丸がフレームの誤差データを表す(次元数はオレンジの丸と同じ)
図中①がソースの"out_value"に該当
図中②がソースの"out_deriv"に該当
図中③がソースの"in_deriv"に該当

誤差逆伝播(2)

続いて、「AffineComponentPreconditionedOnline」コンポーネント

nnet2/nnet-component.cc
in_deriv->AddMatMat(1.0, out_deriv, kNoTrans, linear_params_, kNoTrans, 0.0);

f:id:ichou1:20180617093335p:plain
<図の説明>
図中①がソースの"out_deriv"に該当
図中②がソースの"linear_params_"(モデルのパラメータ部分)に該当
図中③がソースの"in_deriv"に該当

また、入力値と出力誤差をもとにモデルのパラメータを更新する。
f:id:ichou1:20180617093701p:plain

誤差逆伝播(3)

続いて、「Normalize」コンポーネント

nnet2/nnet-component.cc
cu::DiffNormalizePerRow(in_value, out_deriv, BaseFloat(1), false, in_deriv);

f:id:ichou1:20180617094255p:plain
<図の説明>
図中①がソースの"in_value"に該当
図中②がソースの"out_deriv"に該当
図中③がソースの"in_deriv"に該当

誤差逆伝播(4)

続いて、「Pnorm」コンポーネント

nnet2/nnet-component.cc
in_deriv->DiffGroupPnorm(in_value, out_value, out_deriv, p_);

f:id:ichou1:20180617094728p:plain
<図の説明>
図中①がソースの"in_value"に該当
図中②がソースの"out_value"に該当
図中③がソースの"out_deriv"に該当
図中④がソースの"in_deriv"に該当

誤差逆伝播(5)

続いて、「AffineComponentPreconditionedOnline」コンポーネント

nnet2/nnet-component.cc
in_deriv->AddMatMat(1.0, out_deriv, kNoTrans, linear_params_, kNoTrans, 0.0);

f:id:ichou1:20180617095244p:plain
<図の説明>
図中①がソースの"out_deriv"に該当
図中②がソースの"linear_params_"(モデルのパラメータ部分)に該当
図中③がソースの"in_deriv"に該当

また、入力値と出力誤差をもとにモデルのパラメータを更新する。
f:id:ichou1:20180617095318p:plain