λ°μν
μ΄λ²κΈμμλ λ¨μν Layer λΆν° νλ² κ΅¬νν΄ λ³΄κ² μ΅λλ€.
- μμ κΈμμλ³Έ κ³μ° κ·Έλνμ κ³±μ λ Έλλ₯Ό 'MultiLayer', λ§μ λ Έλλ₯Ό 'AddLayer'λΌλ μ΄λ¦μΌλ‘ ꡬνν©λλ€.
κ³±μ κ³μΈ΅
- λͺ¨λ κ³μΈ΅μ forward()μ backward()λΌλ 곡ν΅μ Method(μΈν°νμ΄μ€)λ₯Ό κ°λλ‘ κ΅¬νν©λλ€.
- forward()λ Forward Propagation(μμ ν), backward()λ Back propagation(μμ ν)λ₯Ό μ²λ¦¬ν©λλ€.
- νλ² κ΅¬νν΄ λ³΄κ² μ΅λλ€.
# coding: utf-8
class MulLayer:
def __init__(self):
self.x = None
self.y = None
# xμ yλ₯Ό μΈμλΌ λ°κ³ λ κ°μ κ³±ν΄μ λ°ν
def forward(self, x, y):
self.x = x
self.y = y
out = x * y
return out
# μλ₯μμ λμ΄μ¨ λ―ΈλΆ(dout)μ μμ ν λμ κ°μ
# μλ‘ λ°κΏ κ³±ν ν νλ₯λ‘ νλ €μ€
def backward(self, dout):
dx = dout * self.y # xμ yλ₯Ό λ°κΎΌλ€.
dy = dout * self.x
return dx, dy
- μΈμ€ν΄μ€ λ³μμΈ x,yλ₯Ό μ΄κΈ°ν ν©λλ€. μ΄ λ λ³μλ Forward PropagatIon(μμ ν)μ μ λ ₯ κ°μ μ μ§νκΈ° μν΄μ μ¬μ©ν©λλ€.
- forward()μμλ x, yλ₯Ό μΈμλ‘ λ°κ³ λ κ°μ κ³±ν΄μ λ°ν ν©λλ€.
- λ°λ©΄ backward()μμλ μλ₯μμ λμ΄μ¨ λ―ΈλΆ(dout)μ Forward PropagatIon(μμ ν) λμ κ°μ 'μλ‘ λ΄κΏ' κ³±ν ν νλ₯λ‘ ν립λλ€.
- MulLayerλ₯Ό μ¬μ©νμ¬ μμ νλ₯Ό λ€μκ³Ό κ°μ΄ ꡬνν μ μμ΅λλ€.
# coding: utf-8
from layer_naive import *
apple = 100
apple_num = 2
tax = 1.1
mul_apple_layer = MulLayer()
mul_tax_layer = MulLayer()
# forward
apple_price = mul_apple_layer.forward(apple, apple_num)
price = mul_tax_layer.forward(apple_price, tax)
print(price) # 200
- κ° λ³μμ λν λ―ΈλΆμ backward() μμ ꡬν μ μμ΅λλ€.
# backward (μμ ν)
dprice = 1
dapple_price, dtax = mul_tax_layer.backward(dprice)
dapple, dapple_num = mul_apple_layer.backward(dapple_price)
print(dapple, dapple_num, dtax) # 2.2 110 200
- backward() μμ νμ νΈμΆ μμλ forward() μμ ν λμλ λ°λμ λλ€.
- λ, backward()κ° λ°λ μΈμλ 'μμ νμ μΆλ ₯μ λν λ―ΈλΆ'μμ μ£Όμν©λλ€.
λ§μ κ³μΈ΅
class AddLayer:
def __init__(self):
pass
# μ
λ ₯λ°μ λ μΈμ x, yλ₯Ό λν΄μ λ°ν
def forward(self, x, y):
out = x + y
return out
# μλ₯μμ λ΄λ €μ¨ λ―ΈλΆ(dout)μ κ·Έλλ‘ νλ₯λ‘ νλ €μ€
def backward(self, dout):
dx = dout * 1
dy = dout * 1
return dx, dy
- λ§μ
κ³μΈ΅μμλ μ΄κΈ°νκ° νμ μκΈ° λλ¬Έμ _init_()μμλ μ무 μΌλ νμ§ μμ΅λλ€.
- μ¦, passλ μ무κ²λ νμ§ λ§λΌλ λͺ λ Ήμ λλ€.
- λ§μ κ³μΈ΅μ forward()μμλ μ λ ₯λ°μ λ μΈμ x, yλ₯Ό λν΄μ λ°νν©λλ€.
- backward()μμλ μλ₯μμ λ΄λ €μ¨ λ―ΈλΆ(dout)μ κ·Έλλ‘ νλ₯λ‘ ν릴 λΏμ λλ€.
κ·Έλ¬λ©΄ λ§μ , κ³±μ κ³μΈ΅μ μ¬μ©νμ¬ μ¬κ³Ό 2κ°μ κ·€ 3κ°λ₯Ό μ¬λ μν©μ ꡬνν΄ λ³΄κ² μ΅λλ€.
# coding: utf-8
from layer_naive import *
apple = 100
apple_num = 2
orange = 150
orange_num = 3
tax = 1.1
# layer
mul_apple_layer = MulLayer()
mul_orange_layer = MulLayer()
add_apple_orange_layer = AddLayer()
mul_tax_layer = MulLayer()
# forward
apple_price = mul_apple_layer.forward(apple, apple_num) # (1)
orange_price = mul_orange_layer.forward(orange, orange_num) # (2)
all_price = add_apple_orange_layer.forward(apple_price, orange_price) # (3)
price = mul_tax_layer.forward(all_price, tax) # (4)
# backward
dprice = 1
dall_price, dtax = mul_tax_layer.backward(dprice) # (4)
dapple_price, dorange_price = add_apple_orange_layer.backward(dall_price) # (3)
dorange, dorange_num = mul_orange_layer.backward(dorange_price) # (2)
dapple, dapple_num = mul_apple_layer.backward(dapple_price) # (1)
print("price:", int(price))
print("dApple:", dapple)
print("dApple_num:", int(dapple_num))
print("dOrange:", dorange)
print("dOrange_num:", int(dorange_num))
print("dTax:", dtax)
- νλνλμ λͺ λ Ήμ λ¨μν©λλ€. νμν κ³μΈ΅μ λ§λ€μ΄μ Forward Propagation(μμ ν) MethodμΈ forward()λ₯Ό μ μ ν μμλ‘ νΈμΆν©λλ€.
- κ·Έλ° λ€μ Forward Propagation(μμ ν)μ λ°λ μμλ‘ Back Propagation(μμ ν) MethodμΈ Backward()λ₯Ό νΈμΆνλ©΄ μνλ λ―ΈλΆμ΄ λμ΅λλ€.
Model Code (by Python)
# κ³±μ
κ³μΈ΅ μ μ
class MulLayer:
def __init__(self):
self.x = None # μμ ν μ
λ ₯κ° μ μ§λ₯Ό μν΄μ μ΄κΈ°ν
self.y = None # μμ ν μ
λ ₯κ° μ μ§λ₯Ό μν΄μ μ΄κΈ°ν
def forward(self, x, y):
self.x = x # μμ ν μ μ
λ ₯λ xκ° μ μ₯
self.y = y # μμ ν μ μ
λ ₯λ yκ° μ μ₯
out = x * y # μ
λ ₯λ λ κ°μ κ³± λ°ν
return out
# μλ₯μμ λμ΄μ¨ λ―ΈλΆ(dout)μμ μμ ν λμ κ°μ μλ‘ λ΄κΏ κ³±ν ν νλ₯λ‘ νλ¦Ό
def backward(self, dout):
dx = dout * self.y # xμ λν λ―ΈλΆκ° κ³μ°
dy = dout * self.x # yμ λν λ―ΈλΆκ° κ³μ°
return dx, dy # λ―ΈλΆ κ²°κ³Ό λ°ν
# λ§μ
κ³μΈ΅ μ μ
class AddLayer:
def __init__(self):
pass # λ§μ
κ³μΈ΅μ λ³λμ μ΄κΈ°ν μμ
μ΄ νμ μμ
def forward(self, x, y):
out = x + y # μ
λ ₯λ λ κ°μ ν© λ°ν
return out
# μλ₯μμ λμ΄μ¨ λ―ΈλΆ(dout)μμ μμ ν λμ κ°μ μλ‘ λ΄κΏ κ³±ν ν νλ₯λ‘ νλ¦Ό
def backward(self, dout):
dx = dout * 1 # xμ λν λ―ΈλΆκ° κ³μ°
dy = dout * 1 # yμ λν λ―ΈλΆκ° κ³μ°
return dx, dy # λ―ΈλΆ κ²°κ³Ό λ°ν
if __name__ == '__main__':
# λ¬Έμ 1: μ¬κ³Ό κ°κ²© κ³μ° μμ
apple = 100 # μ¬κ³Ό ν κ° κ°κ²©
apple_num = 2 # μ¬κ³Ό κ°μ
tax = 1.1 # μΈκΈ
# κ³μΈ΅ μμ±
mul_apple_layer = MulLayer() # μ¬κ³Ό κ°κ²© κ³μ°μ μν κ³±μ
κ³μΈ΅
mul_tax_layer = MulLayer() # μΈκΈ κ³μ°μ μν κ³±μ
κ³μΈ΅
# μμ ν
apple_price = mul_apple_layer.forward(apple, apple_num) # μ¬κ³Ό κ°κ²© κ³μ°
price = mul_tax_layer.forward(apple_price, tax) # μ΅μ’
κ°κ²© κ³μ°
print(price) # μ΅μ’
κ°κ²© μΆλ ₯
# μμ ν
dprice = 1 # κ°κ²©μ λν λ―ΈλΆκ° μ΄κΈ°ν
dapple_price, dtax = mul_tax_layer.backward(dprice) # μΈκΈ κ³μ° μμ ν
dapple, dapple_num = mul_apple_layer.backward(dapple_price) # μ¬κ³Ό κ°κ²© κ³μ° μμ ν
print(dapple, dapple_num, dtax) # λ―ΈλΆ κ²°κ³Ό μΆλ ₯
# λ¬Έμ 2: μ¬κ³Όμ μ€λ μ§ κ°κ²© κ³μ° μμ
orange = 150 # μ€λ μ§ ν κ° κ°κ²©
orange_num = 3 # μ€λ μ§ κ°μ
# κ³μΈ΅ μ¬μ¬μ© λ° μλ‘μ΄ κ³μΈ΅ μμ±
mul_apple_layer = MulLayer() # μ¬κ³Ό κ°κ²© κ³μ°μ μν κ³±μ
κ³μΈ΅ (μ¬μ¬μ©)
mul_orange_layer = MulLayer() # μ€λ μ§ κ°κ²© κ³μ°μ μν κ³±μ
κ³μΈ΅
add_apple_orange_layer = AddLayer() # μ¬κ³Όμ μ€λ μ§ κ°κ²© ν©μ°μ μν λ§μ
κ³μΈ΅
mul_tax_layer = MulLayer() # μΈκΈ κ³μ°μ μν κ³±μ
κ³μΈ΅ (μ¬μ¬μ©)
# μμ ν
apple_price = mul_apple_layer.forward(apple, apple_num) # μ¬κ³Ό κ°κ²© κ³μ°
orange_price = mul_orange_layer.forward(orange, orange_num) # μ€λ μ§ κ°κ²© κ³μ°
all_price = add_apple_orange_layer.forward(apple_price,
Activation Function Layer (νμ±ν ν¨μ κ³μΈ΅) ꡬννκΈ°
κ³μ° κ·Έλνλ₯Ό μ κ²½λ§μ μ μ©ν΄ λ³΄κ² μ΅λλ€. μ κ²½λ§μ ꡬμ±νλ Layer(κ³μΈ΅)μ κ°κ°μ ν΄λμ€ νλλ‘ κ΅¬νν©λλ€.
ReLU κ³μΈ΅
- νμ±ν ν¨μλ‘ μ¬μ©λλ ReLUμ μμμ λ€μκ³Ό κ°μ΅λλ€.
- xμ λν yμ λ―ΈλΆμ μλμ μμ²λΌ ꡬν©λλ€.
- μμ μμκ³Ό κ°μ΄, Forward Propagation(μμ ν) λμ μ λ ₯μΈ xκ° 0λ³΄λ€ ν¬λ©΄ Back Propagation(μμ ν)λ μλ₯μ κ°μ κ·Έλλ‘ νλ₯λ‘ ν립λλ€.
- λ€λ§, Forward Propagation(μμ ν) λ xκ° 0 μ΄νλ©΄ Back Propagation(μμ ν) λλ νλ₯λ‘ μ νΈλ₯Ό 보λ΄μ§ μμ΅λλ€. (0μ 보λ λλ€.) κ³μ° κ·Έλνλ‘λ μλμ κ·Έλ¦Όμ²λΌ 그립λλ€.
- μ΄μ νλ² ReLU κ³μΈ¨μ ꡬνν΄ λ³΄κ² μ΅λλ€.
class Relu:
def __init__(self):
self.mask = None # μ
λ ₯κ°μ΄ 0 μ΄νμΈμ§ μ¬λΆλ₯Ό μ μ₯νκΈ° μν λ³μλ₯Ό μ΄κΈ°νν©λλ€.
def forward(self, x):
self.mask = (x <= 0) # xμ κ°μ΄ 0 μ΄νμΈ μμλ True, κ·Έ μΈλ Falseλ‘ νλ λ°°μ΄μ μμ±ν©λλ€.
out = x.copy() # μ
λ ₯κ° xμ 볡μ¬λ³Έμ μμ±ν©λλ€.
out[self.mask] = 0 # maskκ° TrueμΈ μμΉ, μ¦ xμ κ°μ΄ 0 μ΄νμΈ μμΉμ μμλ₯Ό 0μΌλ‘ μ€μ ν©λλ€.
return out # νμ±ν ν¨μλ₯Ό μ μ©ν κ²°κ³Όλ₯Ό λ°νν©λλ€.
def backward(self, dout):
dout[self.mask] = 0 # μμ ν λ 0 μ΄νμλ μμμ λμνλ μμ ν κ°μ 0μΌλ‘ μ€μ ν©λλ€.
dx = dout # λλ¨Έμ§ μμλ κ·Έλλ‘ doutμ λ°νν©λλ€.
return dx # μ
λ ₯κ°μ λν λ―ΈλΆκ°μ λ°νν©λλ€.
- ReLU ν΄λμ€λ maskλΌλ μΈμ€ν΄μ€ λ³μλ₯Ό κ°μ§λλ€.
- maskλ True/Falseλ‘ κ΅¬μ±λ Numpy Array(λ°°μ΄)λ‘, Forward Propagation(μμ ν)μ μ λ ₯μΈ xμ μμ κ°μ΄ 0μ΄νμΈ indexλ True, κ·Έ μΈ(0λ³΄λ€ ν° μμ)λ Falseλ‘ μ μ§ν©λλ€.
- μ컨λ mask λ³μλ True/Falseλ‘ κ΅¬μ±λ Numpy λ°°μ΄μ μ μ§ν©λλ€.
Sigmoid κ³μΈ΅
- Sigmoid ν¨μλ λ€μ μμ μλ―Έν©λλ€.
- μμ μμ κ³μ° κ·Έλνλ‘ κ·Έλ¦¬λ©΄ μλμ κ·Έλ¦Όμ²λΌ λ©λλ€.
- 'x'μ '+' λ Έλλ§κ³ λ, 'exp' ,'/' λ Έλκ° μλλ°, 'exp' λ Έλλ y = exp(x) κ³μ°μ μννκ³ '/' λ Έλλ y = 1/x κ³μ°μ μνν©λλ€.
- κ³μ°μ 'κ΅μμ κ³μ°'μ μ νλ‘ μ΄λ€μ§λλ€. μ΄μ μμ κ³μ° κ·Έλνμ Back Propagation(μμ ν)μ νλ¦μ μ€λ₯Έμͺ½μμ μΌμͺ½μΌλ‘ ν λ¨κ³μ© μΆμ΄λ³΄κ² μ΅λλ€.
1λ¨κ³
- '/' λ Έλ, y = 1/x μ λ―ΈλΆνλ©΄ λ€μ μμ΄ λ©λλ€.
- Back Propagation(μμ ν) λλ μλ₯μμ νλ¬μ¨ κ°μ -y**2 (μμ νμ μΆλ ₯μ μ κ³±ν ν λ§μ΄λμ€λ₯Ό λΆμΈ κ°)μ κ³±ν΄μ νλ₯λ‘ μ λ¬ν©λλ€.
- κ³μ° κ·Έλνμμλ λ€μκ³Ό κ°μ΅λλ€.
2λ¨κ³
- '+'λ Έλλ μλ₯μ κ°μ μ¬κ³Ό μμ΄ νλ₯λ‘ λ΄λ³΄λ΄μ§λκ² λ€μ λλ€.
3λ¨κ³
- 'exp' λ Έλλ y = exp(x) μ°μ°μ μννλ©°, κ·Έ λ―ΈλΆμ λ€μκ³Ό κ°μ΅λλ€.
- κ³μ° κ·Έλνμμλ μλ₯μ κ°μ Forward Propagation(μμ ν) λμ μΆλ΅(μ΄ μμμλ exp(-x))μ κ³±ν΄ νλ₯λ‘ μ νν©λλ€.
4λ¨κ³
- 'x'λ Έλλ Forward Propagation(μμ ν) λμ κ°μ 'μλ‘ λ΄κΏ' κ³±ν©λλ€. μ¬κΈ°μλ -1λ₯Ό κ³±ν©λλ€.
- μμ κ³μ° κ·Έλνλ₯Ό 보면, Sigmoid κ³μΈ΅μ Back Propagation(μμ ν)λ₯Ό κ³μ° κ·Έλνλ₯Ό μμ±νμ΅λλ€.
- μ΄λ¬ν κ³μ° κ·Έλνμ μ€κ° κ³Όμ μ λͺ¨λ λ¬Άμ΄ λ¨μν 'Sigmoid' λ Έλ νλλ‘ λ체ν μ μμ΅λλ€.
- κ³μ° κ·Έλνμ, κ°μν κ·Έλνμ κ°μν λ²μ μ κ²°κ³Όλ κ°μ΅λλ€.
- κ·Έλ μ§λ§, κ°μν λ²μ μ Back Propagation(μμ ν) κ³Όμ μ μ€κ° κ³Όμ μ μλ΅νμ¬ λ ν¨μ¨μ μΈ κ³μ°μ΄λΌκ³ ν μ μμ΅λλ€.
- λν Nodeλ₯Ό κ·Έλ£Ήν νμ¬ Sigmoid κ³μΈ΅μ μΈμΈν λ΄μ©μ λ ΈμΆνμ§ μκ³ μ λ ₯, μΆλ ₯μλ§ μ§μ€ ν μ μλ€λ κ²λ μ’μ ν¬μΈνΈ μ λλ€.
- μ΄μ²λΌ Sigmoid κ³μΈ΅μ Back Propagation(μμ ν)λ Forward Progagation(μμ ν)μ μΆλ ₯(y)λ§μΌλ‘ κ³μ°ν μ μμ΅λλ€.
- κ·Έλ¬λ©΄ νλ² Sigmoid κ³μΈ΅μ PythonμΌλ‘ ꡬνν΄ λ³΄κ² μ΅λλ€.
- μ¬κΈ°μλ Forward Progagation(μμ ν)μ μΆλ ₯μ μΈμ€ν΄μ€ λ³μ outμ 보κ΄νλ€κ°, Back Propagation(μμ ν)λ κ·Έ κ°μ μ¬μ©ν©λλ€.
class Sigmoid:
def __init__(self):
self.out = None # μμ νμ μΆλ ₯κ°μ μ μ₯νκΈ° μν λ³μλ₯Ό μ΄κΈ°νν©λλ€.
def forward(self, x):
out = 1 / (1 + np.exp(-x)) # μκ·Έλͺ¨μ΄λ ν¨μλ₯Ό μ μ©ν©λλ€.
self.out = out # μμ νμ κ²°κ³Όλ₯Ό μ μ₯ν©λλ€. μ΄ κ°μ μμ ν λ μ¬μ©λ©λλ€.
return out # νμ±ν ν¨μλ₯Ό μ μ©ν κ²°κ³Όλ₯Ό λ°νν©λλ€.
def backward(self, dout):
dx = dout * (1.0 - self.out) * self.out # μκ·Έλͺ¨μ΄λ ν¨μμ λ―ΈλΆμ μ μ©ν©λλ€.
return dx # μ
λ ₯κ°μ λν λ―ΈλΆκ°μ λ°νν©λλ€.
# doutμ μλ₯(λ€μ κ³μΈ΅)μμ λμ΄μ¨ λ―ΈλΆκ°μ
λλ€.
# μκ·Έλͺ¨μ΄λ ν¨μμ λ―ΈλΆμ y(1-y)μ΄λ©°, μ¬κΈ°μ yλ μκ·Έλͺ¨μ΄λ ν¨μμ μΆλ ₯κ°μ
λλ€.
# λ°λΌμ, self.outμ΄ yμ ν΄λΉνκ³ , (1.0 - self.out) * self.outμ΄ y(1-y)μ ν΄λΉν©λλ€.
# μ΄λ₯Ό μλ₯μμ λμ΄μ¨ λ―ΈλΆκ°κ³Ό κ³±νμ¬ μ΄ κ³μΈ΅μ ν΅κ³Όν λμ λ―ΈλΆκ°μ ꡬν©λλ€.
Affine κ³μΈ΅
μ κ²½λ§μ Forward Propagation(μμ ν)μμλ Weight(κ°μ€μΉ) μ νΈμ μ΄ν©μ κ³μ°νκΈ° λλ¬Έμ νλ ¬μ κ³±(Numpyμμλ np.dot())μ μ¬μ©νμ΅λλ€.
- Neuron(λ΄λ°)μ Weight(κ°μ€μΉ) ν©μ Y = np.dot(X, W) + Bμ²λΌ κ³μ°ν©λλ€.
- κ·Έλ¦¬κ³ μ΄ Yλ₯Ό Activation Function(νμ±ν ν¨μ)λ‘ λ³νν΄ λ€μ Layer(μΈ΅)μΌλ‘ μ ννλ κ²μ΄ μ κ²½λ§ Forward Propagation(μμ ν)μ νλ¦μ΄μμ΅λλ€.
- νλ ¬μ κ³± κ³μ°μ λμνλ Dimension(μ°¨μ)μ μμ μλ₯Ό μΌμΉμν€λκ² ν΅μ¬μ λλ€. νλ ¬μ νμμ (2, 3)μ²λΌ κ΄νΈλ‘ νκΈ°νλ μ΄λ΄λ Numpy shapeν¨μμ Output(μΆλ ₯) & ννλ₯Ό ν΅μΌνκΈ° μν΄μ μ λλ€.
μ κ²½λ§μ Forward Propagation(μμ ν) λ μννλ νλ ¬μ κ³±μ κΈ°ννμμ Affine Transformation(μ΄νμΈ λ³ν)μ΄λΌκ³ ν©λλ€.
- κ·Έλ¬λ©΄ νλ ¬μ κ³±κ³Ό Bias(νΈν₯)μ ν©μ κ³μ° κ·Έλνλ‘ νλ² κ·Έλ €λ³΄κ² μ΅λλ€.
- κ³±μ κ³μ°νλ λ Έλλ₯Ό 'dot'μ΄λΌ νλ©΄ np.dot(X, W) + B κ³μ°μ μλμ κ·Έλνμ²λΌ κ·Έλ €μ§λλ€.
- μ°Έκ³ λ‘ μ§κΈκΉμ§μ κ³μ° κ·Έλνλ λ Έλ μ¬μ΄μ 'μ€μΉΌλΌ κ°'μ΄ νλ λλ° λ°ν΄, μ΄ μμμλ 'νλ ¬'μ΄ νλ₯΄κ³ μμ΅λλ€.
- κ·Έλ¬λ©΄ μ΄λ²μλ Back propagation(μμ ν)μ λν΄ μκ°ν΄ λ³΄κ² μ΅λλ€.
- νλ ¬μ μ¬μ©ν Back propagation(μμ ν)λ νλ ¬μ μμλ§λ€ μ κ°ν΄λ³΄λ©΄ μ€μΉΌλΌ κ°μ μ¬μ©ν μ§κΈκΉμ§μ κ³μ° κ·Έλνμ κ°μ μμλ‘ μκ°ν μ μμ΅λλ€.
- WTμ Tλ μ μΉνλ ¬μ λ»νλ©°, Wμ (i, j) μμΉμ μμλ₯Ό (j,i) μμΉλ‘ λ΄κΎΌκ²μ λ§ν©λλ€.
- κ³μ°κ·Έλνμμ κ° λ³μμ νμμ μ£Όμν΄μ μ΄ν΄ λ΄μΌ ν©λλ€.
- νΉν Xμ δL/δXμ κ°μ νμμ΄κ³ , Wμ δL/δWλ κ°μ νμμ΄λΌλ κ²μ κΈ°μ΅νμΈμ.
- κ·Όλ°, μ¬κΈ°μ μλ¬Έμ΄ λλκ² μμ΅λλ€. μ νλ ¬μ νμμ μ£Όμλ₯Ό ν΄μΌ ν κΉμ?
- νλ ¬μ κ³±μμ λμνλ μ°¨μμ μμ μλ₯Ό μΌμΉμμΌμΌ νκΈ° λλ¬Έμ λλ€.
λ°°μΉμ© Affine κ³μΈ΅
- Affine κ³μΈ΅μ μ λ ₯ λ°μ΄ν°λ‘ X νλλ§μ κ³ λ €ν κ²μ΄μμ΅λλ€.
- μ΄λ² μ μμλ λ°μ΄ν° Nκ°λ₯Ό λ¬Άμ΄ Forward Propagation(μμ ν)νλ κ²½μ°, μ¦, λ°°μΉμ© Affine κ³μΈ΅μ μκ°ν΄ λ³΄κ² μ΅λλ€.
- μ¬κΈ°μ λ¬Άμ λ°μ΄ν°λ₯Ό 'λ°°μΉ'λΌκ³ λΆλ¦ λλ€.
- κΈ°μ‘΄κ³Ό λ€λ₯Έ λΆλΆμ input(μ λ ₯)μΈ Xμ νμμ΄ (N, 2)κ° λ κ² λΏμ λλ€. κ·Έ λ€λ‘λ μ§κΈκΉμ§μ κ°μ΄ κ³μ° κ·Έλνμ μμλ₯Ό λ°λΌ μμν νλ ¬ κ³μ°μ ν©λλ€.
- λν Back propagation(μμ ν) λλ νλ ¬μ νμμ μ£Όμνλ©΄ δL/δXκ³Ό δL/δWμ μ΄μ κ³Ό κ°μ΄ λμΆν μ μμ΅λλ€.
- νΈνμ λν λλ μ£Όμν΄μΌ ν©λλ€. Forward Propagation(μμ ν)μ Bias(νΈν₯) λ§μ μ X, Wμ λν Bias(νΈν₯)μ΄ κ°κ°μ λ°μ΄ν°μ λν΄μ§λλ€.
- κ·Έλμ Back propagation(μμ ν) λλ κ° λ°μ΄ν°μ Back propagation(μμ ν)κ°μ΄ Bias(νΈν₯)μ μμμ λͺ¨μ¬μΌ ν©λλ€.
- μ΄λ κ² Affine κ³μΈ΅μ μ΄λ κ² κ΅¬ν ν μ μμ΅λλ€.
class Affine:
def __init__(self, W, b):
self.W = W # κ°μ€μΉ(weight)λ₯Ό μ΄κΈ°νν©λλ€.
self.b = b # νΈν₯(bias)μ μ΄κΈ°νν©λλ€.
self.x = None # μ
λ ₯ λ°μ΄ν°λ₯Ό μ μ₯νκΈ° μν λ³μλ₯Ό μ΄κΈ°νν©λλ€.
self.dW = None # κ°μ€μΉμ κΈ°μΈκΈ°λ₯Ό μ μ₯νκΈ° μν λ³μλ₯Ό μ΄κΈ°νν©λλ€.
self.db = None # νΈν₯μ κΈ°μΈκΈ°λ₯Ό μ μ₯νκΈ° μν λ³μλ₯Ό μ΄κΈ°νν©λλ€.
def forward(self, x):
self.x = x # μ
λ ₯ λ°μ΄ν°λ₯Ό μ μ₯ν©λλ€.
out = np.dot(x, self.W) + self.b # μ
λ ₯ λ°μ΄ν°μ κ°μ€μΉμ λ΄μ μ κ³μ°νκ³ νΈν₯μ λν©λλ€.
return out # κ³μ°λ κ²°κ³Όλ₯Ό λ°νν©λλ€.
def backward(self, dout):
dx = np.dot(dout, self.W.T) # μλ₯μμ λμ΄μ¨ λ―ΈλΆκ°μ κ°μ€μΉμ μ μΉλ₯Ό κ³±νμ¬ μ
λ ₯ λ°μ΄ν°μ λν λ―ΈλΆκ°μ κ³μ°ν©λλ€. (μ€ν μμ : np.dout -> np.dot, xelf.W.T -> self.W.T)
self.dW = np.dot(self.x.T, dout) # μ
λ ₯ λ°μ΄ν°μ μ μΉμ μλ₯μμ λμ΄μ¨ λ―ΈλΆκ°μ κ³±νμ¬ κ°μ€μΉμ λν λ―ΈλΆκ°μ κ³μ°ν©λλ€.
self.db = np.sum(dout, axis=0) # μλ₯μμ λμ΄μ¨ λ―ΈλΆκ°μ μΆ(axis) 0μ λ°λΌ ν©μ°νμ¬ νΈν₯μ λν λ―ΈλΆκ°μ κ³μ°ν©λλ€.
return dx # μ
λ ₯ λ°μ΄ν°μ λν λ―ΈλΆκ°μ λ°νν©λλ€.
Softmax-with-Loss κ³μΈ΅
μΆλ ₯μΈ΅μμ μ¬μ©νλ Softmax ν¨μμ κ΄ν΄ μ€λͺ νκ² μ΅λλ€.
- Softmax ν¨μλ μ
λ ₯ κ°μ μ κ·ννμ¬ μΆλ ₯ν©λλ€. μλ₯Ό λ€μ΄μ Mnist λ°μ΄ν°μ
μ νμ©ν μκΈμ¨ μ«μ μΈμμμμ Softmax κ³μΈ΅μ μΆλ ₯μ μλμ κ·Έλ¦Όμ²λΌ λ©λλ€.
- Input Imageκ° Affine κ³μΈ΅, ReLU κ³μΈ΅μ ν΅κ³Όνμ¬ λ³νλκ³ , λ§μ§λ§ Softmax κ³μΈ΅μ μν΄μ 10κ°μ μ λ ₯μ΄ μ κ·ν λ©λλ€.
- μ΄ κ·Έλ¦Όμμλ μ«μ '0'μ μ μλ 5.3μ΄λ©°, μ΄κ²μ΄ Softmax κ³μΈ΅μ μν΄μ 0.008(0.8%)λ‘ λ³νλ©λλ€.
- λν '2'μ μ μλ 10.1μμ 0.991(99.1%)λ‘ λ³νλ©λλ€.
- Softmax κ³μΈ΅μ μ λ ₯ κ°μ μ κ·ν(μΆλ ₯μ ν©μ΄ 1μ΄ λλ‘λ‘ λ³ν)νμ¬ μΆλ ₯ν©λλ€.
- κ·Έλ¦¬κ³ μκΈμ¨ μ«μλ 10κ°(Class 10κ°λ‘ λΆλ₯)μ΄λ―λ‘ Softmax κ³μΈ΅μ μ λ ₯μ 10κ°κ° λ©λλ€.
μ κ²½λ§μμ μννλ μμ μ νμ΅, μΆλ‘ 2κ°μ§ μΈλ°, μΆλ‘ ν λμ μΌλ°μ μΌλ‘ Softmax κ³μΈ΅μ μ¬μ©νμ§ μμ΅λλ€.
μ κ²½λ§μ μΆλ‘ ν λ λ§μ§λ§ Affine κ³μΈ΅μ μΆλ ₯μ μΈμ κ²°κ³Όλ‘ μ΄μ©ν©λλ€.
κ·Έλ¦¬κ³ μ κ²½λ§μμ μ κ·ν νμ§ μλ μΆλ ₯ κ²°κ³Όλ₯Ό Score(μ μ)λΌκ³ ν©λλ€.
μ¦, μ κ²½λ§ μΆλ‘ μμ λ΅μ νλλ§ λ΄λ κ²½μ°μλ κ°μ₯ λμ Score(μ μ)λ§ μλ©΄ λλ, Softmax κ³μΈ΅μ΄ νμ μμ΅λλ€.
λ€λ§, μ κ²½λ§μ νμ΅ν λμλ Softmax κ³μΈ΅μ΄ νμν©λλ€.
- κ·Έλ¬λ©΄ μ΄μ Softmax κ³μΈ΅μ νλ² λ³΄κ² μ΅λλ€. Loss Function(μμ€ ν¨μ)μΈ Cross-Entropy Error(κ΅μ²΄ μνΈλ‘νΌ μ€μ°¨)λ ν¬ν¨νμ¬, 'Softmax-with-Loss κ³μΈ΅'μ΄λΌλ μ΄λ¦μΌλ‘ ꡬνν©λλ€.
- 보μλ€ μνΌ, Softmax-with-Loss κ³μΈ΅μ 볡μ‘ν©λλ€. μ¬κΈ°μλ κ²°κ³Όλ§ νλ² λ³΄κ² μ΅λλ€.
- μμ κ³μ° κ·Έλνμμ μννΈλ§₯μ ν¨μλ 'Softmax" κ³μΈ΅μΌλ‘, Cross-Entropy Error'κ³μΈ΅μΌλ‘ νκΈ°νμ΅λλ€.
- μ¬κΈ°μ 3κ°μ ν΄λμ€ λΆλ₯λ₯Ό κ°μ νκ³ μ΄μ Layer(κ³μΈ΅)μμ 3κ°μ μ λ ₯(Score)λ₯Ό λ°μ΅λλ€.
- κ·Έλ¦Όκ³Ό κ°μ΄ Softmax κ³μΈ΅μ μ λ ₯ (a1, a2, a3)λ₯Ό μ κ·ννμ¬ (y1, y2, y3)λ₯Ό μΆλ ₯ν©λλ€.
- Cross-Entropy Error κ³μΈ΅μ Softmax κ³μΈ΅μ μΆλ ₯ (y1, y2, y3)μ μ λ΅ λ μ΄λΈ (t1, t2, t3)λ₯Ό λ°κ³ , μ΄ λ°μ΄ν°λ‘λΆν° Loss(μμ€) Lμ μΆλ ₯ν©λλ€.
- κ°μνλ Softmax-with-Loss κ³μΈ΅μ κ³μ° κ·Έλνμμ μ£Όλͺ©ν 건 Back propagation(μμ ν)μ κ²°κ³Όμ λλ€.
- Softmax κ³μΈ΅μ Back propagation(μμ ν)λ (y1 - t1, y2- t2, y3 - t3)λΌλ 'λ§λν' κ²°κ³Όλ₯Ό λ΄λκ³ μμ΅λλ€.
- (y1 ~ y3)λ Softmax κ³μΈ΅μ μΆλ ₯μ΄κ³ , (t1 ~ t3)λ μ λ΅ λ μ΄λΈ μ΄λ―λ‘, (y1 - t1, y2- t2, y3 - t3)λ Softmax κ³μΈ΅μ μΆλ ₯κ³Ό μ λ΅ λ μ΄λΈμ μ°¨λΆμΈκ²μ λλ€.
- μ κ²½λ§μ Back propagation(μμ ν)λ μ΄ μ°¨μ΄μΈ μ€μ°¨κ° μ κ³μΈ΅μ μ ν΄μ§λ κ²μ λλ€.
- μ΄κ²μ΄ μ κ²½λ§ νμ΅μ μ€μν μ±μ§μ λλ€.
- κ·Έλ¬λ©΄ Softmax-with-Loss κ³μΈ΅μ ꡬνν μ½λλ₯Ό λ³΄κ² μ΅λλ€.
Softmax-with-Loss Example Code (by Python)
class SoftmaxWithLoss:
def __init__(self):
self.loss = None # μμ€
self.y = None # softmaxμ μΆλ ₯
self.t = None # μ λ΅ λ μ΄λΈ(μ-ν« λ²‘ν°)
def forward(self, x, t):
self.t = t
self.y = softmax(x) # μ
λ ₯ xμ λν΄ softmax ν¨μλ₯Ό μ μ©ν©λλ€.
self.loss = cross_entropy_error(self.y, self.t
# softmaxμ μΆλ ₯κ³Ό μ λ΅ λ μ΄λΈμ μ΄μ©ν΄ ν¬λ‘μ€ μνΈλ‘νΌ μ€μ°¨λ₯Ό κ³μ°ν©λλ€.
return self.loss # κ³μ°λ μμ€μ λ°νν©λλ€.
def backward(self, dout=1):
batch_size = self.t.shape[0] # λ°°μΉ ν¬κΈ°λ₯Ό ꡬν©λλ€.
dx = (self.y - self.t) / batch_size
# μμ€ ν¨μμ λ―ΈλΆμ κ³μ°ν©λλ€. μ¬κΈ°μ dout=1μ μμ€ ν¨μμ λ―ΈλΆκ°μ΄ 1μ΄λΌκ³ κ°μ νκΈ° λλ¬Έμ
λλ€.
return dx # μ
λ ₯κ°μ λν λ―ΈλΆκ°μ λ°νν©λλ€.
- μ£Όμν΄μΌ νλμ μ Back propagation(μμ ν) λλ μ ννλ κ°μ Batch_sizeλ‘ λλ μ λ°μ΄ν° 1κ°λΉ μ€μ°¨λ₯Ό μ Layer(κ³μΈ΅)μΌλ‘ μ νν©λλ€.
Backprogagation(μ€μ°¨μμ ν)λ² κ΅¬ννκΈ°
μ κ²½λ§ νμ΅μ μ 체μ μΈ Flow
λ€μ νλ² μ κ²½λ§ νμ΅μ μμλ₯Ό νλ² λ³΄κ² μ΅λλ€.
μ μ
- μ κ²½λ§μλ μ μ κ°λ₯ν Weight(κ°μ€μΉ)μ Bias(νΈν₯)μ΄ μκ³ , μ΄ Weight(κ°μ€μΉ)μ Bias(νΈν₯)μ Training Data(νλ ¨ λ°μ΄ν°)μ μ μνλλ‘ μ‘°μ νλ κ³Όμ μ Training(νμ΅)μ΄λΌκ³ ν©λλ€.
- κ·Έλ¦¬κ³ Neural Network Training(μ κ²½λ§ νμ΅)μ 4λ¨κ³λ‘ μνν μ μμ΅λλ€.
1λ¨κ³ - Mini-Batch
- νλ ¨ λ°μ΄ν° μ€ μΌλΆλ₯Ό 무μμλ‘ κ°μ Έμ΅λλ€. μ΄λ κ² μ λ³ν λ°μ΄ν°λ₯Ό Mini-Batch(λ―Έλλ°°μΉ) λΌκ³ ν©λλ€.
- κ·Έλ¦¬κ³ κ·Έ Mini-Batch(λ―Έλλ°°μΉ)μ Loss Function Value(μμ€ ν¨μ κ°)μ μ€μ΄λ κ²μ΄ λͺ©νμ λλ€.
2λ¨κ³ - Gradient(κΈ°μΈκΈ°) μ°μΆ
- Mini-Batchμ Loss Function κ°μ μ€μ΄κΈ° μν΄μ κ° Weight Paraemter(κ°μ€μΉ 맀κ°λ³μ)μ Gradient(κΈ°μΈκΈ°)λ₯Ό ꡬν©λλ€.
- Gradient(κΈ°μΈκΈ°)λ Loss Function Value(μμ€ ν¨μ κ°)μ κ°μ₯ μκ² νλ λ°©ν₯μ μ μν©λλ€.
3λ¨κ³ - Parameter(맀κ°λ³μ) κ°±μ
- Weight Paraemter(κ°μ€μΉ 맀κ°λ³μ)λ₯Ό Gradient(κΈ°μΈκΈ°) λ°©ν₯μΌλ‘ μμ£Ό μ‘°κΈ κ°±μ ν©λλ€.
4λ¨κ³ - λ°λ³΅
- 1~3λ¨κ³λ₯Ό λ°λ³΅ν©λλ€.
- μ¬κΈ°μ μ€μ°¨μμ νλ²μ΄ λ±μ₯νλ λ¨κ³λ 2λ¨κ³μΈ 'Gradient(κΈ°μΈκΈ°)μ°μΆ' μ λλ€.
- μμμλ μ΄ Gradient(κΈ°μΈκΈ°)λ₯Ό ꡬνκΈ° μν΄μ μμΉ λ―ΈλΆμ μ¬μ©νμ§λ§, μ€μ°¨μμ νλ²μ μ΄μ©νλ©΄ Gradient(κΈ°μΈκΈ°)λ₯Ό ν¨μ¨μ , λΉ λ₯΄κ² ꡬν μ μμ΅λλ€.
μ€μ°¨μμ νλ²μ μ΄μ©ν μ κ²½λ§ κ΅¬ννκΈ°
μ¬κΈ°μ 2μΈ΅ μ κ²½λ§μ TwoLayerNet ν΄λμ€λ‘ ꡬνν©λλ€. νλ² ν΄λμ€ & μΈμ€ν΄μ€ λ³μ λ° Methodλ₯Ό μ μν νλ€μ μ΄ν΄λ³΄κ² μ΅λλ€.
- μμμΌ ν μ μ, Layer(κ³μΈ΅)μ μ¬μ©νλ€λ μ μ λλ€.
- Layer(κ³μΈ΅)μ μ¬μ©ν¨μΌλ‘μ¨ μΈμ κ²°κ³Όλ₯Ό μ»λ μ²λ¦¬(predict())μ Gradient(κΈ°μΈκΈ°)λ₯Ό ꡬνλ μ²λ¦¬ (gradient()) κ³μΈ΅μ μ νλ§μΌλ‘ λμμ΄ μ΄λ£¨μ΄ μ§λλ€.
# coding: utf-8
import sys, os
sys.path.append(os.pardir) # λΆλͺ¨ λλ ν°λ¦¬μ νμΌμ κ°μ Έμ¬ μ μλλ‘ μ€μ
import numpy as np
from common.layers import *
from common.gradient import numerical_gradient
from collections import OrderedDict
class TwoLayerNet:
def __init__(self, input_size, hidden_size, output_size, weight_init_std = 0.01):
# κ°μ€μΉ μ΄κΈ°ν
self.params = {}
self.params['W1'] = weight_init_std * np.random.randn(input_size, hidden_size)
self.params['b1'] = np.zeros(hidden_size)
self.params['W2'] = weight_init_std * np.random.randn(hidden_size, output_size)
self.params['b2'] = np.zeros(output_size)
# κ³μΈ΅ μμ±
self.layers = OrderedDict()
self.layers['Affine1'] = Affine(self.params['W1'], self.params['b1'])
self.layers['Relu1'] = Relu()
self.layers['Affine2'] = Affine(self.params['W2'], self.params['b2'])
self.lastLayer = SoftmaxWithLoss()
def predict(self, x):
for layer in self.layers.values():
x = layer.forward(x)
return x
# x : μ
λ ₯ λ°μ΄ν°, t : μ λ΅ λ μ΄λΈ
def loss(self, x, t):
y = self.predict(x)
return self.lastLayer.forward(y, t)
def accuracy(self, x, t):
y = self.predict(x)
y = np.argmax(y, axis=1)
if t.ndim != 1 : t = np.argmax(t, axis=1)
accuracy = np.sum(y == t) / float(x.shape[0])
return accuracy
# x : μ
λ ₯ λ°μ΄ν°, t : μ λ΅ λ μ΄λΈ
def numerical_gradient(self, x, t):
loss_W = lambda W: self.loss(x, t)
grads = {}
grads['W1'] = numerical_gradient(loss_W, self.params['W1'])
grads['b1'] = numerical_gradient(loss_W, self.params['b1'])
grads['W2'] = numerical_gradient(loss_W, self.params['W2'])
grads['b2'] = numerical_gradient(loss_W, self.params['b2'])
return grads
def gradient(self, x, t):
# forward
self.loss(x, t)
# backward
dout = 1
dout = self.lastLayer.backward(dout)
layers = list(self.layers.values())
layers.reverse()
for layer in layers:
dout = layer.backward(dout)
# κ²°κ³Ό μ μ₯
grads = {}
grads['W1'], grads['b1'] = self.layers['Affine1'].dW, self.layers['Affine1'].db
grads['W2'], grads['b2'] = self.layers['Affine2'].dW, self.layers['Affine2'].db
return grads
- μΈμλ μ°¨λ‘λλ‘ μ λ ₯μΈ΅ λ΄λ° μ, μλμΈ΅ λ΄λ° μ, μΆλ ₯μΈ΅ λ΄λ° μ, κ°μ€μΉ μ΄κΈ°ν μ μ κ·λΆν¬μ μ€μΌμΌμ λλ€.
- OrderedDictλ μμκ° μλ λμ λλ¬ μ λλ€. 'μμκ° μλ' λμ λ리μ μΆκ°ν μμλ₯Ό κΈ°μ΅νλ€λ κ²μ λλ€.
- κ·Έλμ Forward Propagation(μμ ν) λλ μΆκ°ν μμλλ‘ κ° Layer(κ³μΈ΅)μ forward() Methodλ₯Ό νΈμΆνλ©΄ μ²λ¦¬κ° λ©λλ€.
- Back Propagation(μμ ν)λμλ Layer(κ³μΈ΅)μ λ°λ μμλ‘ νΈμΆ νκΈ°λ§ νλ©΄ λ©λλ€.
- Affine, ReLU κ³μΈ΅μ΄ κ°μμ λ΄λΆμμ Forward Propagation(μμ ν), Back Propagation(μμ ν)λ₯Ό μ²λ¦¬νκ³ μμΌλκΉ, κ·Έλ₯ κ³μΈ΅μ μ¬λ°λ₯Έ μμλ‘ μ°κ²°ν ν νΈμΆν΄μ£Όλ©΄ λμ λλ€.
Gradient(κΈ°μΈκΈ°) κ²μ¦νκΈ°
- ν¬κ² 2κ°μ§ λ°©λ²μ΄ μμ΅λλ€.
- μμΉ λ―ΈλΆμ μ¨μ Gradient(κΈ°μΈκΈ°)λ₯Ό ꡬνλ λ°©λ², ν΄μμ μΌλ‘ μμμ νμ΄μ Gradient(κΈ°μΈκΈ°)λ₯Ό ꡬνλ λ°©λ² 2κ°μ§κ° μμ΅λλ€.
- μμμ νμ΄μ ꡬνλ λ°©λ²μ μ€μ°¨μμ νλ²μ μ¬μ©ν΄μ 맀κ°λ³μκ° λ§μλ ν¨μ¨μ μΌλ‘ κ³μ°μ΄ κ°λ₯ν©λλ€.
- μ¬κΈ°μ μμΉ λ―ΈλΆμ μ€μ°¨μμ νλ²μ κ²°κ³Όλ₯Ό λΉκ΅νμ¬ μ λλ‘ κ΅¬ννλμ§ κ²μ¦νλ κ³Όμ μ κ±°μΉ©λλ€.
- μ΄ κ²μ¦νλ μμ μ 'κΈ°μΈκΈ° νμΈ(Gradient Check)'λΌκ³ ν©λλ€.
# coding: utf-8
import sys, os
sys.path.append(os.pardir) # λΆλͺ¨ λλ ν°λ¦¬μ νμΌμ κ°μ Έμ¬ μ μλλ‘ μ€μ
import numpy as np
from dataset.mnist import load_mnist
from two_layer_net import TwoLayerNet
# λ°μ΄ν° μ½κΈ°
(x_train, t_train), (x_test, t_test) = load_mnist(normalize=True, one_hot_label=True)
network = TwoLayerNet(input_size=784, hidden_size=50, output_size=10)
x_batch = x_train[:3]
t_batch = t_train[:3]
grad_numerical = network.numerical_gradient(x_batch, t_batch)
grad_backprop = network.gradient(x_batch, t_batch)
# κ° κ°μ€μΉμ μ°¨μ΄μ μ λκ°μ ꡬν ν, κ·Έ μ λκ°λ€μ νκ· μ λΈλ€.
for key in grad_numerical.keys():
diff = np.average( np.abs(grad_backprop[key] - grad_numerical[key]) )
print(key + ":" + str(diff))
# Result
W2:9.71260696544e-13
b2:1.20570232964e-10
W1:2.86152966578e-13
b1:1.19419626098e-12
μμΉ λ―ΈλΆκ³Ό μ€μ°¨μμ νλ²μΌλ‘ ꡬν κΈ°μΈκΈ°μ μ°¨μ΄κ° λ§€μ° μλ€.
μ€μ μμ΄ κ΅¬νλμμ νλ₯ μ΄ λλ€.
μ λ°λκ° μ ννκΈ° λλ¬Έμ μ€μ°¨κ° 0μ΄ λμ§λ μλλ€.
μ€μ°¨μμ νλ²μ μ΄μ©ν νμ΅ κ΅¬ννκΈ°
μ§κΈκΉμ§μ λ€λ₯Έ λΆλΆμ Grdient(κΈ°μΈκΈ°)λ₯Ό μ€μ°¨μμ νλ²μΌλ‘ ꡬνλ€λ μ λΏμ λλ€.
# coding: utf-8
import sys, os
sys.path.append(os.pardir)
import numpy as np
from dataset.mnist import load_mnist
from two_layer_net import TwoLayerNet
# λ°μ΄ν° μ½κΈ°
(x_train, t_train), (x_test, t_test) = load_mnist(normalize=True, one_hot_label=True)
network = TwoLayerNet(input_size=784, hidden_size=50, output_size=10)
# hyperparameter
iters_num = 10000 # λ°λ³΅νμ
train_size = x_train.shape[0]
batch_size = 100 # λ―Έλλ°°μΉ ν¬κΈ°
learning_rate = 0.1
train_loss_list = []
train_acc_list = []
test_acc_list = []
# 1 epochλΉ λ°λ³΅νλ νμ
iter_per_epoch = max(train_size / batch_size, 1)
for i in range(iters_num):
# λ―Έλλ°°μΉ νλ
batch_mask = np.random.choice(train_size, batch_size)
x_batch = x_train[batch_mask]
t_batch = t_train[batch_mask]
# μ€μ°¨μμ νλ²μΌλ‘ κΈ°μΈκΈ° κ³μ° (λ³κ²½ν λΆλΆ)
#grad = network.numerical_gradient(x_batch, t_batch) # μμΉ λ―ΈλΆ λ°©μ
grad = network.gradient(x_batch, t_batch) # μ€μ°¨μμ νλ² λ°©μ(ν¨μ¬ λΉ λ₯΄λ€)
# 맀κ°λ³μ κ°±μ
for key in ('W1', 'b1', 'W2', 'b2'):
network.params[key] -= learning_rate * grad[key]
# νμ΅ κ²½κ³Ό κΈ°λ‘
loss = network.loss(x_batch, t_batch)
train_loss_list.append(loss)
# 1epoch λΉ accuray κ³μ°
if i % iter_per_epoch == 0:
train_acc = network.accuracy(x_train, t_train)
test_acc = network.accuracy(x_test, t_test)
train_acc_list.append(train_acc)
test_acc_list.append(test_acc)
print(train_acc, test_acc)
# Result
"""
train acc, test acc | 0.0992833333333, 0.1032
train acc, test acc | 0.898, 0.9026
train acc, test acc | 0.92135, 0.9216
train acc, test acc | 0.936016666667, 0.9337
train acc, test acc | 0.945316666667, 0.9431
train acc, test acc | 0.94675, 0.9427
train acc, test acc | 0.954766666667, 0.9521
train acc, test acc | 0.9602, 0.9551
train acc, test acc | 0.9634, 0.9581
train acc, test acc | 0.9656, 0.9597
train acc, test acc | 0.9683, 0.9615
train acc, test acc | 0.970516666667, 0.9629
train acc, test acc | 0.97305, 0.9649
train acc, test acc | 0.9731, 0.9661
train acc, test acc | 0.975916666667, 0.9659
train acc, test acc | 0.976383333333, 0.9666
train acc, test acc | 0.977916666667, 0.969
[Finished in 45.5s]
"""
Summary
- κ³μ° κ·Έλνλ₯Ό μ΄μ©νλ©΄ κ³μ° κ³Όμ μ μκ°μ μΌλ‘ νμ ν μ μμ΅λλ€.
- κ³μ° κ·Έλνμ λ Έλλ κ΅μμ κ³μ°μΌλ‘ ꡬμ±λ©λλ€. κ΅μμ κ³μ°μ μ‘°ν©ν΄ μ 체 κ³μ°μ ꡬμ±ν©λλ€.
- κ³μ° κ·Έλνμ μμ νλ ν΅μμ κ³μ°μ μνν©λλ€. ννΈ, κ³μ° κ·Έλνμ μμ νλ‘λ κ° λ Έλμ λ―ΈλΆμ ꡬν μ μμ΅λλ€.
- μ κ²½λ§μ κ΅¬μ± μμλ₯Ό κ³μΈ΅μΌλ‘ ꡬννμ¬ κΈ°μΈκΈ°λ₯Ό ν¨μ¨μ μΌλ‘ κ³μ°ν μ μμ΅λλ€(μ€μ°¨μμ νλ²).
- μμΉ λ―ΈλΆκ³Ό μ€μ°¨μμ νλ²μ κ²°κ³Όλ₯Ό λΉκ΅νλ©΄ μ€μ°¨μμ νλ²μ ꡬνμ μλͺ»μ΄ μλμ§ νμΈν μ μμ΅λλ€(κΈ°μΈκΈ° νμΈ).
λ°μν
'π₯οΈ Deep Learning' μΉ΄ν κ³ λ¦¬μ λ€λ₯Έ κΈ
[DL] Activation Function - νμ±ν ν¨μ (0) | 2024.04.29 |
---|---|
[DL] Feed-forward Network (νΌλ-ν¬μλ λ€νΈμν¬) (0) | 2024.04.18 |
[DL] Backpropagation (μ€μ°¨μμ νλ²) (0) | 2024.03.27 |
[DL] Gradient (κΈ°μΈκΈ°), Training Algorithm(νμ΅ μκ³ λ¦¬μ¦) (0) | 2024.03.23 |
[DL] Neural Network Training (μ κ²½λ§ νμ΅) (0) | 2024.03.21 |