Weight Normalization [arXiv:1602.07868]

2016年10月23日

概要

はじめに

Weight Normalizationは、ニューラルネットの重みベクトル$\boldsymbol w$を

のように、ベクトル$\boldsymbol v$とスカラー$g$に分解します。

また、これらのパラメータで誤差関数$L$を微分した時の勾配はそれぞれ

となります。

ここで$\circ$は要素積の総和を表します。numpy.dotではありませんのでご注意下さい。

実装

実装する際はchainerのfunctionを継承したクラスを作成し、式(2)の$\nabla_{\boldsymbol w}L$を親クラスのfunctionに計算させます。

その後自クラスで$\nabla_gL$と$\nabla_{\boldsymbol v}L$を計算するだけで実装は完了です。

またWeight Normalizationは重みベクトルに対して行う操作のようなので、重み行列を用いるchainerのLinkでは$g$はスカラーではなく出力ユニット数の次元を持ったベクトルになります。

畳み込みニューラルネットの場合は出力チャネルごとに$\boldsymbol v$があるとみなして$g$の次元数は出力チャネル数と同じにするようです。

Data-Dependent Initialization

Weight Normalizationではパラメータ$g$やニューラルネットのバイアス$b$をデータから決まる値で初期化します。

私の実装では最初にデータを入力したときに自動的に初期化されるようにしてあるので、学習を始める前に一度訓練データを入力してください。

終わりに

最近のGenerative Adversarial Networkは、DiscriminatorにWeight Normalizationを使う例が多かったため今回作成しました。

一応テストも書き、(というかchainerのLink用テストをコピペして精度を少し落としただけ)ちゃんと通るのを確認したのでバグはないと思います。