機械学習とかコンピュータビジョンとか

CVやMLに関する勉強のメモ書き。

Glow: Generative Flow with Invertible 1×1 Convolutionsを読んだのでメモ

はじめに

Glow: Generative Flow with Invertible 1×1 Convolutionsを読んだのでメモ. VAEやAdamでお馴染みのDr. DP.Kingmaの論文.生成された顔画像が高周波成分までしっかりと表現しており衝撃的.

位置付け

イントロダクションに生成モデルについて完結まとまっていたのでまずはそこから. まず,尤度に基づいた方法は以下の3種類に分類される.

  • Autoregressive models
  • Variational autoencoders
  • Flow-based generative models

Autoregressive modelsはモデルの簡潔さに利点があるが,並列性(GPUで高速化できるかどうか)に限界があり計算量の観点から高次元のデータ生成はやりにくい.また,VAEは並列性に優れているが最適化が難しい.それぞれ利点と欠点がある.ではflow-based generative modelsはどうかというところ.flow-basedには以下の4つの利点があるとのこと(問題点は触れられてなかったが,モデル立てる上で逆変換とヤコビアン行列式の計算に制約があることか).

  • 潜在変数の推定と対数尤度を評価に近似が入らない
  • 推定と生成においてGPUで並列化可能
  • downstreamなタスクにおいて有用な潜在変数空間を持つ
  • メモリ効率が良い

そこでこのflow-basedの良さに目をつけ,generative flowであるGlowを提案している.

Flow-based Generative Models

何度もメモを残したが今一度flow-based generative modelsについて.\mathbf{x}を未知の分布\mathbf{x}\sim p^*(\mathbf{x})を持つ高次元の確率変数とし,そのような確率変数をデータセット\mathcal{D}からi.i.dに取得したとする.この時パラメータ\mathbf{\theta}を持つモデルp_\mathbf{\theta}(\mathbf{x})で近似することを考える.\mathbf{x}が離散データの場合には,最小化する対数尤度関数は

\displaystyle
\mathcal{L}\mathcal(D)=\frac{1}{N}\sum_i^N-\log p_\mathbf{\theta}(\mathbf{x}^{(i)})

で与えられる.連続の場合には近似的に

\displaystyle
\mathcal{L}\mathcal(D)\simeq\frac{1}{N}\sum_i^N-\log p_\mathbf{\theta}(\tilde{\mathbf{x}}^{(i)})+c

として与えられる.ただし\tilde{\mathbf{x}}^{(i)}=\mathbf{x}^{(i)}+u,\:u\sim\mathcal{U}(0,a),\:c=-M\log a満たす(M\mathbf{x}の次元で,aはデータの離散具合から決定される).

Flow-basedモデルにおいては生成過程は以下のように定義される.

\displaystyle
\mathbf{z}\sim p_\mathbf{\theta}(\mathbf{z}) \\ \displaystyle
\mathbf{x}=\mathbf{g}_\mathbf{\theta}(\mathbf{z})

つまるところ確率変数の変数変換.基本的にはp_\mathbf{\theta}(\mathbf{z})は扱いやすい密度関数である多変量の球面ガウス分布p_\mathbf{\theta}(\mathbf{z})=\mathcal{N}(\mathbf{z};0,\mathbf{I})などを考える.一つの強い制約として関数g_\mathbf{\theta}全単射でなければならない.すなわち\mathbf{z}=f_\mathbf{\theta}(\mathbf{x})=g_\mathbf{\theta}^{-1}(\mathbf{x})という関係が成り立つ必要がある.

上記の関係から,データ\mathbf{z}と潜在変数\mathbf{z}には次のような関係が成り立つ.

\displaystyle
\mathbf{x}\overset{f_1}{\longleftrightarrow}\mathbf{h}_1\overset{f_2}{\longleftrightarrow}\mathbf{h}_2\dots\overset{f_K}{\longleftrightarrow}\mathbf{z}

そこからおなじみの変数変換の公式を使えば以下の対数密度関数が得られる.

\displaystyle
\log p_\mathbf{\theta}(\mathbf{x})
=\log p_\mathbf{\theta}(\mathbf{z})+\log|\mathrm{det}(d\mathbf{z}/d\mathbf{x})|
=\log p_\mathbf{\theta}(\mathbf{z})+\sum_i^K\log\left|\mathrm{det}\left(\frac{d\mathbf{h}_i}{d\mathbf{h}_{i-1}}\right)\right|

ただし,\mathbf{h}_0=\mathbf{x},\:\mathbf{h}_K=\mathbf{z}として定義. 一般的なアプローチとしてヤコビアンの計算を楽にするためにヤコビアンが三角行列になるような変換を選ぶ.

Glow

ここから本題のGlow.Glowは以下の3つのモジュールから構成されており,それらをRealNVPと同様にマルチスケールに組み合わせている.

  • actnorm
  • invertible 1\times1 convolution
  • coupling layer

Actnormは誤解を恐れず言えばbatch normの正規化の単位がチャネルになったもの.ただし,ミニバッチが入力される度にチャネルごとの平均と分散を計算することはなく,スケールとバイアスパラメータを一番最初のミニバッチのチャネルごとの平均と分散を使って初期化を行う(data dependent initializationとして別な論文で議論されている初期化方法らしい).そのため,いわゆるrunning_mean等の値は保持しない.またcoupling layerはNICEやRealNVPで使われていたaffine coupling layerを使っている.

この論文のメインのコントリビューションはタイトルにもあるようinvertible 1\times1 convolution.一言で言えば,変数変換における制約(逆変換可能)とヤコビアン行列式の計算しやすさを持つ畳み込み.invertible convolutionは適当な回転行列で初期化されるc\times cの重みを持つ.回転行列として初期化するのは行列式を1にしたいため(学習はじめは変数変化によって分布が変化しないようにということかと).それに対しh\times w\times c次元の入力データ\mathbf{h}が与えられた時,ヤコビアン行列式は以下のように計算ができる.

\displaystyle
\log\left|\mathrm{det}\left(\frac{d\mathrm{conv2D}(\mathbf{h};\mathbf{W})}{d\mathbf{h}}\right)\right|=hw\log|\mathrm{det}(\mathbf{W})|

しかし,このままでは計算コストのオーダーとして\mathcal{O}(c^3)となるので一工夫としてLU分解を使う. LU分解は正方行列を上三角行列\mathbf{U}と下三角行列\mathbf{L}の行列積に分解するというもの.

\displaystyle
\mathbf{W}=\mathbf{P}\mathbf{L}(\mathbf{U}+\mathrm{diag}(\mathbf{s}))

\mathbf{P}は置換行列で\mathrm{diag}(\mathbf{s})\mathbf{s}を対角成分に持つ対角行列,\mathbf{L}は対角成分が1の下三角行列.注意として,\mathrm{diag}(\mathbf{s})が吐き出されているため\mathbf{U}の対角成分はゼロになっている.このように分解ができれば\log|\mathrm{det}(\mathbf{W})|=\sum\log|\mathbf{s}|と計算ができるため,計算コストのオーダーが\mathcal{O}(c)になる.このLU分解が成り立たなければいけないため,初期値を回転行列としLU分解を計算して,分解によって現れた各々の値を最適化していく.ただし置換行列だけは固定とする(ここも工夫の一つ).論文のTable 1に各々のモジュールの計算式が載っているから一応そこをみれば何やっているかはすぐわかる.

まとめ

Glowを読んだ.基本的にはRealNVPの枠組みにinvertible convを追加したという話の気がする(あとact normも).それだけでRealNVPに比べてここまで生成結果がよくなるのも驚き.一部腑に落ちない点として,逆変換を行うときにconvの重み行列の逆行列を求める必要があるがそこの計算量については言及されてなかったのはどうなのか(学習後に一度求めてしまえば後は関係ないからいいのか?).

何はともあれflow-basedな生成モデルは確率変数の変数変換の使い方が個人的にとても賢く思えて,ここ最近で一番勉強していて楽しかった.