의견.png

"역전파"의 두 판 사이의 차이

위키원
이동: 둘러보기, 검색
36번째 줄: 36번째 줄:
 
위의 식에서 <math>{dy \over du} = 2u</math>이고, <math>{du \over dx}=1</math>로, 최종적으로 <math>{dy \over dx}=2u=2(x+a)</math>가 된다.
 
위의 식에서 <math>{dy \over du} = 2u</math>이고, <math>{du \over dx}=1</math>로, 최종적으로 <math>{dy \over dx}=2u=2(x+a)</math>가 된다.
  
==단순한 계층 구현==
+
==계층 구현==
 +
===단순한 계층 구현===
 
모든 계층은 forward()와 backward()라는 공통의 메서드를 갖도록 구현한다.
 
모든 계층은 forward()와 backward()라는 공통의 메서드를 갖도록 구현한다.
  
===곱셈 계층===
+
====곱셈 계층====
 
  class MulLayer: # 곱셈 layer
 
  class MulLayer: # 곱셈 layer
 
   def__init__(self):
 
   def__init__(self):
54번째 줄: 55번째 줄:
 
   return dx, dy
 
   return dx, dy
  
===덧셈 계층===
+
====덧셈 계층====
 
  class AddLayer:
 
  class AddLayer:
 
   def__init__(self):
 
   def__init__(self):
65번째 줄: 66번째 줄:
 
   by = dout * 1
 
   by = dout * 1
 
   return dx, dy
 
   return dx, dy
 +
 +
===활성화 함수 계층 구현===
 +
====ReLU 계층====
 +
ReLU 수식은 다음과 같다.
 +
<math>y=x</math> <math>\mbox{if }</math> <math> x>0</math>
 +
  <math>=0</math> <math>\mbox{if }</math> <math> x\leqq 0</math>
 +
 +
ReLU의 미분은 <math>1</math> <math>\mbox{if }</math> <math>x>0</math>, <math>0</math> <math>\mbox{if }</math> <math>x \leqq</math>, 이는 순전파 때의 입력인 <math>x</math>가 <math>0</math>보다 크면 역전파는 상류의 값을 그대로 하류로 흘린다. 반대로 순전파 때 <math>x</math>가 <math>0</math>이하면 역전파 때는 하류로 신호를 보내지 않는다.
 +
 +
class ReLU:
 +
  def__init__(self):
 +
  self.mask = NOne
 +
  def foward(self, x):
 +
  self.mask = (x <= 0)
 +
  out = x.copy()
 +
  out[self.mask] = 0
 +
  return out
 +
def backward(self, dout):
 +
  dout[self.mask] = 0
 +
  dx = dout
 +
  return dx
  
 
{{각주}}
 
{{각주}}

2019년 9월 24일 (화) 14:16 판

역전파(Backpropagation)는 먼저 계산 결과와 정답의 오차를 구해 이 오차에 관여하는 값들의 가증치를 수정하여 오차가 작아지는 방향으로 일정 횟수를 반복해 수정하는 방법이다. 오차역전파 또는 오류역전파라고도 불린다.[1]

개요

역전파 알고리즘은 사슬 규칙을 이용하는 기울기 기반 최적화 알고리즘에 따라 인공신경망(ANN)을 효율적으로 훈련시키는 데 사용되는 방법이다. 이 역전파의 주요 특징은 학습 중인 작업을 수행할 수 있을 때까지 네트워크를 개선하기 위해 가중치 업데이트를 계산하는 반복적이고 재귀적이며 효율적인 방법이다. 역전파는 네트워크 설계 시 활성화 함수의 파생물을 알아야 한다. 자동 미분은 파생물을 훈련 알고리즘에 자동 및 분석적으로 제공할 수 있는 기술이다.[2]

구동 방식

  1. 임의의 초기 가중치()를 준 뒤 결과 ()를 계산한다.
  2. 계산 결과와 우리가 원하는 값 사이의 오차를 구한다.
  3. 경사 하강법을 이용해 바로 앞 가중치를 오차가 작아지는 방향으로 업데이트한다.
  4. 위 과정을 더이상 오차가 줄어들지 않을 때까지 반복한다.

여기서 '오차가 작아지는 방향으로 업데이트한다'는 의미는 미분 값이 0에 가까워지는 방향으로 나아간다는 말이다. 즉, '기울기가 0이 되는 방향'으로 나아가야 하는데, 이 말은 가중치에서 기울기를 뺐을 때 가중치의 변화가 전혀 없는 상태를 말한다. 따라서 오차역전파를 다른 방식으로 표현하자면 가중치에서 기울기를 빼도 값의 변화가 없을 때까지 계속해서 가중치 수정 작업을 반복하는 것이다. 이를 수식으로 표현하면 즉, 새 가중치는 현 가중치에서 '가중치에 대한 기울기'를 뺀 값이다.[3]

종류

  • 덧셈 노드 : 덧셈 노드의 역전파는 입력 값을 그대로 흘려보낸다.
  • 곱셈 노드 : 곱셈 노드의 역전파는 상류의 값에 순전파 때의 입력 신호들을 '서로 바꾼 값"을 곱해서 하류로 보낸다. 순전파때 가 곱해졌다면 역전파에서는 를, 반대로 순전파때 가 곱해졌다면 역전파때 를 곱해서 전달한다. (한 노드에 Input이 들어가서 가 나온다고 하면, 쪽으로는 가 곱해진 값이 전달되고, 쪽으로는 가 곱해진 값이 전달된다.)

계산 그래프

계산 그래프(Computational Graph)란 계산 과정을 그래프로 나타낸 것이다. 그래프는 자료구조의 일종으로 여러 개의 노드(node)와 그 노드들을 잇는 선, 엣지(edge)로 표현된다. 계산 그래프를 이용한 문제 풀이는 다음 흐름으로 진행된다.

  1. 계산 그래프를 구성한다.
  2. 그래프에서 계산을 왼족에서 오른쪽으로 진행한다.

여기서 왼족에서 오른쪽으로 진행하는 단계를 순전파(forward propagation)라고 한다. 순전파는 계산 그래프의 출발점부터 종작첨으로의 전파이다. 또한 반대 방향(오른쪽에서 왼쪽)의 전파도 가능한데, 이를 역전파라고 한다. 역전파는 이후의 미분을 계산할 때 중요한 역할을 한다.

계산 그래프의 특징은 '국소적 계산'을 전파함으로써 최종 결과를 얻는다는 점에 있다. 국소적이란 '자신과 직접 관계된 작은 범위'라는 뜻이다. 국소적 계산은 결국 전체에서 어떤 일이 벌어지든 상관없이 자신과 관계된 정보만으로 결과를 출력할 수 있다는 것이다. 국소적 계산은 단순하지만, 그 결과를 전달함으로써 전체를 구성하는 복잡한 계산을 해낼 수 있다. 계산 그래프의 이점 중 하나는 '국소적 계산'이다. 전체가 아무리 복잡해도 각 노드에서는 단순한 계산에 집중하여 문제를 단순화 할 수 있다. 또 다른 이점으로는, 계산 그래프는 중간 계산 결과를 모두 보관할 수 있다. 마지막으로 실제 계산 그래프를 사용하는 가장 큰 이유는 역전파를 통해 '미분'을 효율적으로 계산할 수 있다는 것이다.

연쇄법칙

역전파는 '국소적인 비문'을 순방향과는 반대인 오른쪽에서 왼쪽으로 전달한다. 또한, 이 국소적 미분을 전달하는 원리는 연쇄법칙(Chain rule)에 따른 것이다. 연쇄법칙은 계산 그래프 상의 역전파와 같다. 역전파의 계산 절차는 전달되는 신호에 노드의 국소적 미분을 곱한 후 다음 노드로 전달하는 것이다. 여기서 말하는 국소적 미분은 순전파 때의 미분을 구한다는 것이다. 연쇄법칙을 설명하려면 합성 함수 이야기부터 시작해야 한다. 합성 함수란 여러 함수로 구성된 함수이다. 예를 들어 라는 식은 다음 두개의 식으로 구성된다.



연쇄법칙은 합성 함수의 미분에 대한 성질이며, 다음과 같이 정의된다. "합성 함수의 미분은 합성 함수를 구성하는 각 함수의 미분의 곱으로 나타낼 수 있다." 이것이 연쇄법칙의 원리이다. 예를 들어 위에 식에서 에 대한 의 미분은, 에 대한 의 미분과 에 대한 의 미분의 곱으로 나타낼 수 있다.


위의 식에서 이고, 로, 최종적으로 가 된다.

계층 구현

단순한 계층 구현

모든 계층은 forward()와 backward()라는 공통의 메서드를 갖도록 구현한다.

곱셈 계층

class MulLayer: # 곱셈 layer
 def__init__(self):
  seif.x = None
  self.y = None
def foward(self,x,y):
  seif.x = x
  seif.y = y
  out = x * y
  return out
def backward(self, dout):# x와 y를 바꾸어 계산
  dx = dout * self.y
  dy = dout * self.x
  return dx, dy

덧셈 계층

class AddLayer:
 def__init__(self):
  pass # 아무일도 하지 말라는 명령어
 def forward(self, x, y):
  out = x + y
  return out
def backward(self, dout):
 dx = dout * 1
 by = dout * 1
 return dx, dy

활성화 함수 계층 구현

ReLU 계층

ReLU 수식은 다음과 같다.

  
    

ReLU의 미분은 , , 이는 순전파 때의 입력인 보다 크면 역전파는 상류의 값을 그대로 하류로 흘린다. 반대로 순전파 때 이하면 역전파 때는 하류로 신호를 보내지 않는다.

class ReLU:
 def__init__(self):
  self.mask = NOne
 def foward(self, x):
  self.mask = (x <= 0)
  out = x.copy()
  out[self.mask] = 0
  return out
def backward(self, dout):
 dout[self.mask] = 0
 dx = dout
 return dx

각주

  1. eccjang, 〈오차역전파〉, 《인코덤》, 2019-01-07
  2. Backpropagation〉, 《위키피디아》
  3. 모두의 딥러닝〉, 《더북》

참고자료

같이 보기

  의견.png 이 역전파 문서는 알고리즘에 관한 토막글입니다. 위키 문서는 누구든지 자유롭게 편집할 수 있습니다. [편집]을 눌러 이 문서의 내용을 채워주세요.