본문 바로가기

Artificial Intelligence/Tensorflow

[Tensorflow] 경사 하강법이 뭐야?

728x90

경사 하강법은 비용 함수가 최소가 되는 w, b를 구하는 방법으로 점진적으로 반복적인 계산을 통해 w, b의 값을 업데이트하면서 오류 값이 최소가 되는 w, b를 구합니다. 다음은 비용 함수입니다.

 

<그림 1 cost(w,b)>

경사 하강법의 특징은 다음과 같습니다.

  • <그림 1>의 최솟값을 찾는다.
  • 변수가 여러 개 일 때에도 사용 가능하다.

경사 하강법은 다음의 방법으로 진행됩니다.

  1. cost(w, b)를 계산한다.
  2. 최솟값이 아니라면 w, b를 cost(w, b)가 줄어드는 방향으로 값을 변경해준다.
  3. 1의 과정을 반복한다. 만약 1의 결과가 최소점이라면 종료한다.

<그림 2 경사하강법 진행 이미지> 이미지 출처: Adam Harley

<그림 2>는 경사 하강법의 진행과정을 GIF 파일로 표현하는 것입니다. 경사 하강법을 위의 그림처럼 진행시키기 위해서는 최솟값을 판별하는 법을 알아야 합니다. 경사 하강법에서의 그래프는 x축이 w, b의 값 y축이 cost(w, b)의 값으로 표현됩니다. 따라서 cost(w,b)가 최소가 되는지 알아보기 위해서는 cost(w,b)의 기울기를 구해야합니다. 기울기를 구하기 위해서는 미분을 해야하므로 cost(w,b)의 식을 미분하기 편하게 바꿔주겠습니다.

 

<그림 3 변경된 cost(w,b)>

<그림 3>처럼 m → 2m으로 바꾼다고 해서 cost(w, b)의 값의 특징이 바뀌지는 않습니다. 손실 함수를 미분하기 편하게 바뀌주었으니 미분을 진행하겠습니다. 미분한 식은 다음과 같습니다. 이때, w,b = W로 치환하여 진행하겠습니다. 

 

<그림 4 손실 함수 미분식>

<그림 4>에 보이는 alpha는 학습률(learning rate)로 <그림 4>의 값을 실제 식에 얼마큼 반영할 것인지 알려주는 변수입니다. 학습률은 적정한 값을 설정하여야 하는데 보통 0.01로 설정합니다. 너무 적게 설정하면 학습이 너무 느리게 진행되고 너무 크게 설정하면 손실 함수의 값이 줄어들지 않고 더 커지게 되는 오버 슈팅(overf shooting) 현상이 발생합니다.

 

W의 값을 cost(W)가 줄어드는 방향으로 값을 변경해주어야 하기 때문에 W의 값에서 <그림 4>의 값을 빼줍니다. 빼주는 이유는 기울기가 음수라면 양의 방향에 최솟값이 존재하다는 것이고, 기울기가 양수라면 음의 방향에 최소값이 존재하기 때문입니다. W의 값을 변경해주는 식은 다음과 같습니다.

 

<그림 5 W값 변경식>

<그림 5>를 더 축약하면 <그림 6>처럼 변하게 됩니다.

 

<그림 6 그림 5 축약식>

경사 하강법을 구현하는 방법에 대해 알아보았으니 이번에는 경사 하강법 구현을 해보겠습니다. 코드는 다음과 같습니다.

 

X = np.array([1.,2.,3.,4.])
Y = np.array([2.,4.,6.,8.])

def cost_func(W, X, Y):
  c = 0
  for i in range(len(X)):
    c += (W * X[i] - Y[i]) ** 2
    return c / len(X)*2

W = tf.Variable([10.0])
epochs = 500

for step in range(epochs + 1):
  hypothesis = X * W
  cost = tf.reduce_mean(tf.square(hypothesis - Y ))

  alpha = 0.01
  gradient = tf.reduce_mean(tf.multiply(tf.multiply(W, X) - Y, X))
  descent = W - tf.multiply(alpha, gradient)
  W.assign(descent)

  if step % 10 == 0:
    print("{:5} | {:10.5} | {:10.5}".format(step, cost.numpy(), W.numpy()[0]))

 

alpha값은 학습률, cost_func는 손실 함수 그리고 hypothesis는 y = 2x입니다. 따라서 경사 하강법을 통해 기대할 수 있는 값은 W = 2가 됩니다. 코드를 실행시켜보면 대략 160번째부터는 2.0의 값을 찾아 더 이상 W의 값이 변경되지 않는 것을 확인할 수 있습니다.

 

참고자료

텐서플로우로 시작하는 딥러닝 기초 강의 - edwith 

728x90