前回まで考察したのは,1変数関数とその導関数の値を計算する場合だった.今回は,2変数関数とその偏導関数を計算する場合について考える.
自動微分を考える前に、2変数関数の微分(偏微分)と演算、関数の合成との関係を見ておこう。2つの変数を \(u\), \(v\) とおく.偏導関数は,変数を添字にして表すことにする.
もとの関数 | 偏導関数 |
---|---|
\(h(u,v)=\mathrm{const.}\) | \(h_u(u,v)=0,\quad h_v(u,v)=0\) |
\(h(u,v)=u\) | \(h_u(u,v)=1,\quad h_v(u,v)=0\) |
\(h(u,v)=v\) | \(h_u(u,v)=0,\quad h_v(u,v)=1\) |
\(h(u,v)=f_1(u,v)\pm f_2(u,v)\) | \(\begin{aligned} h_u(u,v)&=f_{1u}(u,v)\pm f_{2u}(u,v), \\ h_v(u,v)&=f_{1v}(u,v)\pm f_{2v}(u,v) \end{aligned}\) |
\(h(u,v)=f_1(u,v)f_2(u,v)\) | \(\begin{aligned} h_u(u,v)&=f_{1u}(u,v)f_2(u,v)+f_1(u,v)f_{2u}(u,v), \\ h_v(u,v)&=f_{1v}(u,v)f_2(u,v)+f_1(u,v)f_{2v}(u,v) \end{aligned}\) |
\(h(u,v)=f_1(u,v)/f_2(u,v)\) | \(\begin{aligned} h_u(u,v)&=(f_{1u}(u,v)f_2(u,v)-f_1(u,v)f_{2u}(u,v))/f_2(u,v)^2, \\ h_v(u,v)&=(f_{1v}(u,v)f_2(u,v)-f_1(u,v)f_{2v}(u,v))/f_2(u,v)^2 \end{aligned}\) |
\(h(u,v)=g(f(u,v))\) | \(\begin{aligned} h_u(u,v)&=g'(f(u,v))f_u(u,v), \\ h_v(u,v)&=g'(f(u,v))f_v(u,v) \end{aligned}\) |
\(h(u,v)=g(f_1(u,v),f_2(u,v))\) | \(\begin{aligned} h_u(u,v)&=g_x(f_1(u,v),f_2(u,v))f_{1u}(u,v)+g_y(f_1(u,v),f_2(u,v))f_{2u}(u,v), \\ h_v(u,v)&=g_x(f_1(u,v),f_2(u,v))f_{1v}(u,v)+g_y(f_1(u,v),f_2(u,v))f_{2v}(u,v) \end{aligned}\) |
2変数の自動微分を表すときに必要な情報は
- 関数の値 \(f(u,v)\)
- 関数の \(u\) による偏微分係数 \(f_u(u,v)\)
- 関数の \(v\) による偏微分係数 \(f_v(u,v)\)
の3つである。そこで、\(\mathbf{R}\) の自動微分を表す型を \(\mathrm{AutoDiff2}\mathbf{R}=\mathbf{R}\times\mathbf{R}\times\mathbf{R}\) とおき、演算を定義する。上の関係式の \(f_1\),\(f_2\) とその微分係数を \((x,x_u,x_v),(y,y_u,y_v)\in\mathrm{AutoDiff2}\mathbf{R}\) で置き換えると、\(\mathrm{AutoDiff2}\mathbf{R}\) に入れるべき演算が分かる:\begin{align*}
(x,x_u,x_v)\pm(y,y_u,y_v)&=(x\pm y,x_u\pm y_u,x_v\pm y_v) \\
(x,x_u,x_v)\cdot(y,y_u,y_v)&=(x y,x_u y+x y_u,x_v y+x y_v) \\
(x,x_u,x_v)/(y,y_u,y_v)&=(x/y,(x_u y-x y_u)/y^2,(x_v y-x y_v)/y^2)
\end{align*}\(g\colon\mathbf{R}\to\mathbf{R}\) に対し,\[
g_*((x,x_u,x_v))=(g(x),g'(x)x_u,g'(x)x_v),\]
\(g\colon\mathbf{R}\times\mathbf{R}\to\mathbf{R}\) に対し,\[
g_*((x,x_u,x_v),(y,y_u,y_v))=(g(x,y),g_x(x,y)x_u+g_y(x,y)y_u,g_x(x,y)x_v+g_y(x,y)y_v)
\]
Haskellで実装すると,たとえば次のようになる:
[sourcecode lang=”plain”]
data AutoDiff2 a = AutoDiff2 a a a deriving(Eq)
instance Num a => Num (AutoDiff2 a) where
(AutoDiff2 f f_u f_v) + (AutoDiff2 g g_u g_v) = AutoDiff2 (f+g) (f_u+g_u) (f_v+g_v)
(AutoDiff2 f f_u f_v) – (AutoDiff2 g g_u g_v) = AutoDiff2 (f-g) (f_u-g_u) (f_v-g_v)
(AutoDiff2 f f_u f_v) * (AutoDiff2 g g_u g_v) = AutoDiff2 (f*g) (f_u*g+f*g_u) (f_v*g+f*g_v)
abs _ = undefined
signum _ = undefined
fromInteger n = AutoDiff2 (fromInteger n) 0 0
[/sourcecode]
さて、1変数の場合の自動微分(\(\mathbf{R}\times\mathbf{R}\) に演算を入れる)についてもう一度見てみよう。\begin{align*}
(x_0,x_1)\pm(y_0,y_1)&=(x_0\pm y_0,x_1\pm y_1) \\
(x_0,x_1)\cdot(y_0,y_1)&=(x_0 y_0,x_1 y_0+x_0 y_1) \\
(x_0,x_1)/(y_0,y_1)&=(x_0/y_0,(x_1 y_0-x_0 y_1)/y_0^2),
\end{align*}\(g\colon\mathbf{R}\to\mathbf{R}\)(微分可能) に対し、\[g_*((x_0,x_1))=(g(x_0),g'(x_0)x_1),\]\(g\colon\mathbf{R}\times\mathbf{R}\to\mathbf{R}\)(微分可能) に対し、\[g_*((x_0,x_1),(y_0,y_1))=(g(x_0,y_0),g_x(x_0,y_0)x_1+g_y(x_0,y_0)y_1),\]
であった。
よく見てみると、第2成分の \(x_1\), \(y_1\) は \(\mathbf{R}\) でなくても,\(\mathbf{R}\)-ベクトル空間なら何でもよいことが分かる。2変数の偏微分の自動微分は、\(x_1\), \(y_1\) として \(\mathbf{R}^2\) の元をとったものだと考えることができる。一般に、\(n\) 変数の自動微分は \(x_1\), \(y_1\) として \(\mathbf{R}^n\) の元をとることにより得られる。