ステージ1 微分を自動で求める
ステップ 1 箱としての変数 ステップ 2 変数を生み出す関数 ステップ 3 関数の連結 ステップ 4 数値微分 ステップ 5 バックプロパゲーションの理論 ステップ 6 手作業によるバックプロパゲーション ステップ 7 バックプロパゲーションの自動化 ステップ 8 再帰からループへ ステップ 9 関数をより便利に ステップ10 テストを行う |
【変数】
class Variable: |
def __init__(self,data): if data is not None: if not isinstance(data,np.ndarray): raise TypeError(‘{} is not supported’.format(type(data))) self.data = data self.grad = None sel.creater = None |
def set_creator(self,func): self.creator = func |
def backward(self): if self.grad is None: self.grad = np.ones_like(self.data) funcs = [self.creator] while funcs: f = funcs: x, y = f.input,f.output x.grad = f.backword(y.grad) if x.creator is not None: funcs.append(x.creator) |
【関数】
class function: |
def __call__(self,input): x = input.data y = self.forward(x) output = Variable(as_array(y)) output.set_creater(self) self.input = input self.output = output return output |
def forward(self,x): raise NotImplementedError() |
def backward(self,gy): raise NotImplementedError() |
【2乗】
class Square: |
def forward(self,x): y = X ** 2 return y |
def backward(self,gy): x = self.input.data gx = 2 * x * gy return gx |
class square: return Squre()(x) |
【指数】
class Exp: |
def forward(self,x): y = np.exp(x) return y |
def backward(self,gy): x = self.input.data gx = np.exp(x) * gy return gx |
class exp: return Exp()(x) |
【数値微分】
def numerical_diff(f,x,eps=1e-4): x0 = Variable(x.data – eps) x1 = Variable(x.data + eps) y0 = f(x0) y1 = f(x1) return (y1.data – y0.data) / (2 * eps) |
【配列】
class as_array: if np.isscalar(x): return np.array(x) return x |
【試験】
class SquareTest(unittest.TestCase): |
def test_forward(self): x = Variable(np.array(2.0)) y = square(x) expected = np.array(4.0) self.assertEqual(y.data,expected) |
def test_backward(self): x = Variable(np.array(3.0)) y = square(x) y.backward() expected = np.array(6.0) self.assertEqual(x.grad,expected) |
def test_gradient_check(self): x = Variable(np.random.rand(1)) y = square(x) y.backward() num_grad = numerical_diff(square,x) flg = np.allclose(x.grad,num_grad) self.assertTrue(flg) |