728x90
반응형

 지금까지 계단 함수, 선형 함수, 시그모이드 함수, 소프트맥스 함수, 하이퍼볼릭 탄젠트 함수에 대해 다뤄보았다. 이들은 은닉층에서 사용해서는 안되거나, 사용할 수 있더라도 제한적으로 사용해야 하는 활성화 함수들이었다. 이번 포스트에서는 은닉층에서 많이 사용되는 렐루 함수에 대해 학습해 보겠다.

 

 

 

렐루 함수(Rectified Linear Unit, ReLU)

  • 렐루 함수는 딥러닝 역사에 있어 한 획을 그은 활성화 함수인데, 렐루 함수가 등장하기 이전엔 시그모이드 함수를 활성화 함수로 사용해서 딥러닝을 수행했다.
  • 그러나, 이전 포스트에서 언급했듯 시그모이드 함수는 출력하는 값의 범위가 0에서 1사이므로, 레이어를 거치면 거칠수록 값이 현저하게 작아지게 되어 기울기 소실(Vanishing gradient) 현상이 발생한다고 하였다.
    gooopy.tistory.com/52?category=824281
 

머신러닝-3.1. 활성화함수(2)-시그모이드 함수

 지난 포스트에서 퍼셉트론의 가장 기본이 되는 활성화 함수인 계단 함수(Step Function)를 학습하였으며, 선형 함수(Linear Function)의 한계점에 대해서도 학습해보았다.  선형 함수는 층을 쌓는 것이

gooopy.tistory.com

  • 이 문제는 1986년부터 2006년까지 해결되지 않았으나, 제프리 힌튼 교수가 제안한 렐루 함수로 인해, 시그모이드의 기울기 소실 문제가 해결되게 되었다.
  • 렐루 함수는 우리 말로, 정류된 선형 함수라고 하는데, 간단하게 말해서 +/-가 반복되는 신호에서 -흐름을 차단한다는 의미다.
  • 렐루 함수는 은닉층에서 굉장히 많이 사용되는데, 별생각 없이 다층 신경망을 쌓고, 은닉층에 어떤 활성화 함수를 써야 할지 모르겠다 싶으면, 그냥 렐루 함수를 쓰라고 할 정도로, 아주 많이 사용되는 활성화 함수이다(물론 신경망을 의도를 가지고 써보고 싶다면, 그래선 안된다.).

 

 

 

 

1. 렐루 함수의 생김새

  • 렐루 함수는 +신호는 그대로 -신호는 차단하는 함수라고 하였는데, 그 생김새는 아래와 같다.

$$ h(x) = \begin{cases}
 x \ \ \ (x>0) \\ 
 0 \ \ \ (x\leq 0) 
\end{cases} $$

  • 말 그대로, 양수면 자기 자신을 반환하고, 음수면 0을 반환한다.
  • 이번에는 이를 구현해보고, 어떻게 생겼는지 확인해보자.
>>> import numpy as np

# ReLU 함수를 구현해보자
>>> def ReLU(x):
    
>>>     return np.maximum(0, x)
  • 단순하게 최댓값 함수를 사용하여 지금 들어온 값(원소별 연산이 된다!)이 0보다 크면 자기 자신을 반환하고, 그렇지 않으면, 최댓값인 0을 반환하는 함수를 이용해서 구현하였다.
>>> import matplotlib.pyplot as plt

>>> x = np.arange(-5.0, 5.0, 0.1)
>>> y = ReLU(x)

>>> fig = plt.figure(figsize=(8,6))
>>> fig.set_facecolor('white')

>>> plt.title("ReLU", fontsize=30)
>>> plt.xlabel('x', fontsize = 15)
>>> plt.ylabel('y', fontsize = 15, rotation = 0)
>>> plt.axvline(0.0, color='gray', linestyle="--", alpha=0.8)
>>> plt.axhline(0.0, color='gray', linestyle="--", alpha=0.8)
>>> plt.plot(x, y)
>>> plt.show()

  • 가장 많이 사용되는 활성화함수라기엔 지금까지 보아왔던 시그모이드, 소프트맥스, 하이퍼볼릭 탄젠트 등에 비해 너무 단순하게 생겼다는 생각이 들 것이다.
  • 그렇다면 왜 렐루 함수를 은닉층에서 많이 사용할까?

 

 

 

 

2. 렐루 함수를 은닉층에서 많이 사용하는 이유

 

기울기 소실(Vanishing Gradient) 문제가 발생하지 않는다.

  • 렐루 함수는 양수는 그대로, 음수는 0으로 반환하는데, 그러다 보니 특정 양수 값에 수렴하지 않는다. 
  • 즉, 출력값의 범위가 넓고, 양수인 경우 자기 자신을 그대로 반환하기 때문에, 심층 신경망인 딥러닝에서 시그모이드 함수를 활성화 함수로 사용해 발생한 문제였던 기울기 소실(Vanishing Gradient) 문제가 발생하지 않는다.

 

기존 활성화 함수에 비해 속도가 매우 빠르다

  • 동시에 렐루 함수의 공식은 음수면 0, 양수면 자기 자신을 반환하는 아주 단순한 공식이다 보니, 경사 하강 시 다른 활성화 함수에 비해 학습 속도가 매우 빠르다!
  • 확률적 경사하강법(SGD)을 쓴다고 할 때, 시그모이드 함수나 하이퍼볼릭 탄젠트 함수에 비해 수렴하는 속도가 약 6배 가까이 빠르다고 한다!
  • ReLU가 나오기 전에는 활성화 함수가 부드러워야(Smooth) 가중치 업데이트가 잘된다고 생각하여 exp 연산이 들어간 시그모이드나, 하이퍼볼릭 탄젠트 함수를 사용하여쓰나, 활성화 함수가 부드러운(Smooth)한 구간에 도달하는 순간 가중치 업데이트 속도가 매우 느려진다.
  • ReLU는 편미분(기울기) 시 1로 일정하므로, 가중치 업데이트 속도가 매우 빠르다.

 

 

 

 

3. 렐루 함수의 한계점

  • 렐루 함수의 그래프를 보면, 음수 값이 들어오는 경우 모두 0으로 반환하는 문제가 있다보니, 입력값이 음수인 경우 기울기도 모조리 0으로 나오게 된다.
  • 입력값이 음수인 경우에 한정되긴 하지만, 기울기가 0이 되어 가중치 업데이트가 안되는 현상이 발생할 수 있다.
  • 즉, 가중치가 업데이트 되는 과정에서 가중치 합이 음수가 되는 순간 ReLU는 0을 반환하기 때문에 해당 뉴런은 그 이후로 0만 반환하는 아무것도 변하지 않는 현상이 발생할 수 있다.
  • 이러한 죽은 뉴런(Dead Neuron)을 초래하는 현상을 죽어가는 렐루(Dying ReLU) 현상이라고 한다.
  • 또한 렐루 함수는 기울기 소실 문제 방지를 위해 사용하는 활성화 함수이기 때문에 은닉층에서만 사용하는 것을 추천한다.
  • ReLU의 출력값은 0 또는 양수이며, ReLU의 기울기도 0 또는 1이므로, 둘 다 양수이다. 이로 인해 시그모이드 함수처럼 가중치 업데이트 시 지그제그로 최적의 가중치를 찾아가는 지그재그 현상이 발생한다.
  • 또, ReLU의 미분은 0 초과 시, 1 0은 0으로 끊긴다는 문제가 있다. 즉, ReLU는 0에서 미분이 불가능하다.
    (이에 대해 활성화 함수로는 미분 불가능 하다할지라도, 출력값 문제는 아니고, 0에 걸릴 확률이 적으니, 이를 무시하고 사용한다.)

 

 

 

 지금까지 은닉층에서 주로 사용되는 활성화 함수인 렐루 함수에 대해 학습해보았다. 비록 렐루 함수가 입력값이 0일 때, 기울기가 0에 수렴해 가중치 업데이트가 안 되는 현상이 발생한다고는 하지만, 성능상 큰 문제가 없으며, 도리어 이를 해결하기 위해 만든 활성화 함수의 성능이 보다 안 나오는 경우도 있다고 한다.

 때문에 기본적으로 은닉층에서는 렐루 함수를 사용하지만, 때에 따라 렐루 함수의 단점이 두드러지는 경우도 존재하므로, 렐루 함수의 한계점을 보완하기 위한 렐루 함수의 형제 함수들이 있다. 

 다음 포스트에서는 렐루 함수의 한계점을 극복하기 위해 만들어진 다양한 활성화 함수에 대해 학습해보도록 하곘다.

728x90
반응형
728x90
반응형

 지난 포스트에서 퍼셉트론의 가장 기본이 되는 활성화 함수인 계단 함수(Step Function)를 학습하였으며, 선형 함수(Linear Function)의 한계점에 대해서도 학습해보았다.

 선형 함수는 층을 쌓는 것이 무의미해진다는 단점이 있고, 비선형함수 중 하나인 계단 함수는 값의 크기에 대한 정보가 소실된다는 단점이 있다.

 이번 포스트에서는 이 두 단점이 해결된 비선형 함수 중 하나인 시그모이드 함수에 대해 학습해보겠다.

 

 

시그모이드 함수(Sigmoid Function)

계단 함수는 출력을 0과 1로 이진 값만 반환하며, 그 사이에 있는 값은 무시한다는 단점이 있었다. 그렇다면, 앞서 봤던 계단 함수의 각진 부분이 매끄러워진다면 어떨까?

 

 

 

1. 로지스틱 회귀 모델과 오즈(Odds)

  • 통계학을 조금이라도 공부해봤거나, 분석에 관심 있는 사람이라면, 이진 분류의 대표적인 모델 중 하나인 로지스틱 회귀(Logistic regression)에 대해 들어봤거나, 알고 있을 것이다.
  • 시그모이드 함수를 설명하기 앞서 로지스틱 회귀 모델의 오즈(Odds)를 이야기 해보겠다.

 

 

오즈(Odds)

  • 오즈는 성공과 실패의 비율이다.
  • 확률(Probability)과 뉘앙스가 꽤 다른 확률로
  • "사건 A가 일어날 확률 / 사건 A가 일어나지 않을 확률"을 말한다.

$$ Odds = \frac{P}{1-P} $$

 

 

오즈비(Odds ratio)

  • 참고로 오즈비(Odds ratio)와 오즈(Odds)를 헷갈리는 경우가 종종 있는데, 오즈비는 우리말로 교차비라고 하며, 서로 다른 집단의 오즈를 비교할 때 사용된다.
  • 예를 들어 약품의 성능 대한 오즈비는, "약품 A를 먹어서 호전될 오즈 / 위약을 먹어서 호전될 오즈"이다.
  Favorable UnFavorable Total
Test 60 40 100
Control 20 80 100

$$ Test\ favorable\ Odds = \frac{Test\ favorable\ ratio}{Test\ unfavorable\ ratio} = \frac{\frac{60}{100}}{\frac{40}{100}} = 1.5$$

$$ Control\ favorable\ Odds = \frac{Control\ favorable\ ratio}{Control\ unfavorable\ ratio} = \frac{\frac{20}{100}}{\frac{80}{100}}=0.25$$

$$ OddsRatio = \frac{Test\ favorable\ Odds}{Control\ favorable\ Odds} = \frac{1.5}{0.25} = 6.0 $$

  • 위 예시를 보면, 약품A의 효과는 위약의 효과의 6.0배임을 알 수 있다.

 

 

로짓 변환.

  • 오즈에 자연로그를 취해서 로짓(Logit) 함수를 만들어보자.

$$ logit(P) = ln\frac{p}{1-p} = f(x) $$

$$ \frac{p}{1-p} = e^{f(x)},\ \  p=e^{f(x)}(1-p),\ \  p=e^{f(x)} - pe^{f(x)}, \ \  p(1+e^{f(x)})=e^{f(x)} $$

$$ p = \frac{e^{f(x)}}{1+e^{f(x)}} = \frac{1}{1+e^{-{f(x)}}} $$

  • 위 함수를 로지스틱 시그모이드 함수(Logistic sigmoid function)이라고 하며, 줄여서 시그모이드 함수(Sigmoid function)이라고 한다.
  • 여기서 $f(x)$에 회귀 분석과 같은 함수 식을 넣으면, 로지스틱 회귀 모델(Logistic Regression model)이 된다.

$$ f(x) = w^Tx = w_0x_0 + w_1x_1 + w_2x_2 +\ ... + w_mx_m  $$

 

 

 

 

2. 시그모이드 함수(Sigmoid Function)

  • 시그모이드 함수를 파이썬에서 구현해보자.
# 시그모이드 함수
>>> def sigmoid(x):
>>>     return 1 / (1 + np.exp(-x))
>>> x = np.arange(-10.0, 10.0, 0.1)
>>> y = sigmoid(x)

# 캔버스 설정
>>> fig = plt.figure(figsize=(8,7)) # 캔버스 생성
>>> fig.set_facecolor('white')      # 캔버스 색상 설정

>>> plt.plot(x, y)
>>> plt.ylim(-0.1, 1.1)
>>> plt.xlim(-10, 10)
>>> plt.title("Sigmoid", fontsize=30)
>>> plt.xlabel('x', fontsize=20)
>>> plt.ylabel('y', rotation=0, fontsize=20)

>>> plt.yticks([0.0, 0.5, 1.0]) # 특정 축에서 특정 값만 나오게
>>> plt.axvline(0.0, color='k')
>>> ax = plt.gca()
>>> ax.yaxis.grid(True) # y축에 있는 모든 숫자에 회색 점근선을 그음

>>> plt.show()

  • 시그모이드 함수는 0에서 1 사이의 함수이며, 값이 들어왔을 때, 0~1 사이의 값을 반환한다.
  • 연속형 데이터이기 때문에 계단 함수가 끊기지 않는 매끄러운 모양으로 바뀐 것을 알 수 있다.
  • 동시에 이상치가 들어온다 할지라도, 시그모이드 함수는 0과 1에 수렴하므로, 이상치 문제도 해결하면서, 연속된 값을 전달할 수 있다.
  • 시그모이드 함수를 활성화 함수로 사용하면, 0과 1에 가까운 값을 통해 이진 분류를 할 수 있다.

 

 

 

 

3. 시그모이드 함수의 장점과 단점

A. 장점

  • 출력 값의 범위가 0 ~ 1 사이이며, 매우 매끄러운 곡선을 가지므로, 후술 할 경사하강법을 시행할 때, 기울기가 급격하게 변해서 발산하는, 기울기 폭주(Gradient Exploding)가 발생하지 않는다.
  • 분류는 0과 1로 나뉘며, 출력 값이 어느 값에 가까운지를 통해 어느 분류에 속하는지 쉽게 알 수 있다.

 

B. 단점

  • 입력값이 아무리 크더라도, 출력되는 값의 범위가 매우 좁기 때문에 경사하강법 수행 시에 범위가 너무 좁아, 0에 수렴하는 기울기 소실(Gradient Vanishing)이 발생할 수 있다.

  B.1. 기울기 소실(Gradient Vanishing) 문제

  • 시그모이드 함수는 아무리 큰 값이 들어온다 할지라도 0~1사이의 값만 반환하므로, 값이 일정 비율로 줄어들어 값의 왜곡이라 할 수는 없으나, 값이 현저하게 줄어들게 된다. 
  • 또한, 출력 값의 중앙값이 0이 아닌 0.5이며, 모두 양수기 때문에 출력의 가중치 합이 입력의 가중치 합보다 커지게 된다.
  • 이를 편향 이동(Bias Gradient)라 하고, 신호가 각 레이어를 통과할 때마다 분산이 계속 커지게 되어, 활성화 함수의 출력이 최댓값과 최솟값인 0과 1에 수렴하게 된다.
  • 시그모이드 함수의 도함수는 $\sigma(1-\sigma)$인데, 도함수에 들어가는 함수의 값이 0이나 1에 가까울수록 당연히 출력되는 값이 0에 가까워지게 된다.
  • 이로 인해 수렴되는 뉴련의 기울기(Gradient) 값이 0이 되고, 역전파 시 0이 곱해져서 기울기가 소멸(kill)되는 현상이 발생해버린다! 즉, 역전파가 진행될수록 아래 층(Layer)에 아무런 신호가 전달되지 않는 것이다!
  • 이를 기울기 소실(Gradient Vanishing)이라 하며, 렐루 함수가 등장하기 전까지인 1986년부터 2006년까지 해결되지 않은 문제다.

  B.2. 학습 속도 저하 문제

  • 시그모이드 함수의 출력값은 모두 양수기 때문에 경사하강법을 진행할 때, 그 기울기가 모두 양수거나 음수가 된다. 이는 기울기 업데이트가 지그재그로 변동하는 결과를 가지고 오고, 학습 효율성을 감소시켜 학습에 더 많은 시간이 들어가게 만든다.

 

 

 

 위 시그모이드 함수의 장단점을 간추려보면, 출력값이 너무 작아 제대로 학습이 안되는데다가 시간도 많이 잡아먹는다는 소리다.

 이는, 출력층에서 시그모이드 함수를 사용하는 것은 상관 없으나, 아래로 정보가 계속 흘러가는 은닉층(Hidden Layer)에서는 시그모이드 함수를 활성화 함수로 사용해서는 안된다는 소리다.

  • 은닉층(Hidden Layer)은 입력층(시작), 출력층(끝) 사이에 있는 부분이다.
  • 즉, 은닉층에는 앞서 말했던 선형 함수와 시그모이드 함수는 사용하지 않는 것이 좋다.
  • 시그모이드 함수는 이진 분류를 하고자 하는 경우 출력층에서만 사용하는 것을 권고한다.
  • 만약, 입력층에서 시그모이드 함수를 쓰고자 한다면, 이의 발전형인 하이퍼볼릭 탄젠트 함수를 사용하는 것을 추천한다.

 

 

 

 

 

 이번 포스트에서는 시그모이드 함수에 대해 간략하게 알아보았다. 시그모이드 함수는 이진 분류가 목적인 학습 모델에서 출력층에서 사용하는 것을 추천한다. 다음 포스트에서는 또 다른 활성화 함수인 소프트맥스 함수에 대해 학습해보겠다.

728x90
반응형

+ Recent posts