본문 바로가기
machine learning

[TENSORFLOW] Autoencoder

by 유주원 2017. 4. 18.

Autoencoder는 출력을 가능한한 입력에 가깝에 만들도록 매개변수를 학습하는 신경망 유형 중의 하나이다.

예를 들어 아래와 같은 뉴런 모형이 있다면 입력과 출력의 값은 일치하게 될 것이다.

하지만 위와 같은 모델은 어떠한 이득이나 어떠한 특징도 없기 때문에 위와 같은 모델을 autoencoder라고 하지는 않는다.

input과 output 사이에는 작은 차원의 hidden layer가 있고, 이 hidden layer를 통해 input의 특징을 구분지을 수가 있다. 위와 같은 모델을 autoencoder라고 하며, input->hidden으로 데이터를 압축하는 과정을 encoding, hidden->output으로 데이터를 복호화하는 과정을 decoding이라고 부른다.

코드를 통해 살펴보자.

선언문부터 살펴보자. 새롭게 sklearn이란 패키지를 추가했는데, sklearn에서 제공하는 iris data를 train 데이터로 사용하기 위함이다. 만약에 설치가 되어 있지 않다면, 아래와 같이 설치하자.

$> pip install sklearn

Autoencoder class를 살펴보자.

class 생성시 epoch, learning_rate, batch_size 등을 파라미터로 받아서 저장을 한다. encode, decode에 대한 namescope를 각각 지정해주었는데, 이를 통해 weights, biases는 각각의 namescope에 해당하는 다른 변수가 된다. 

encode에서는 input data 1개의 특징 벡터와 hidden node 개수를 곱한 만큼의 weight와 hidden node 개수만큼의 bias 그리고 입력 값 x 와 weight의 매트릭스 곱에 bias를 더한 후 tanh를 씌운 모델을 encoded로 지정했다.

decode에서는 hidden node와 input data 1개의 특징 벡터의 곱 만큼의 weight, input 특징 벡터개의 bias, 그리고 encoded 결과에 weight를 매트릭스 곱한 후 bias를 더한 모델을 decode로 지정한다.

loss는 x에서 decode 결과와의 차이를 제곱한 것의 평균으로 잡았고(MSE) gradient descent 알고리즘은 RMSPropOptimizer를 사용했다. RMSPropOptimizer에 대해 간략히 설명하기 위해서는 우선 Adaptive Gradient에 대한 설명이 필요한데, Adaptive gradient(줄여서 Adagrad)는 학습률을 조절하여 지금까지 많이 변화한 변수의 경우 값을 세밀하게 조절하기 위해 적게 이동시키고, 적게 변화한 변수일수록 optimum에 빨리 도달시키기 위해 많이 이동시키는 알고리즘 이다. 

이를 위해 Adagrad에서는 지금까지 변수가 이동한 gradient의 합의 제곱에 root를 씌워 반비례하게 동작시키는데, 시간이 지날수록 gradient 합의 제곱 값이 커지게 되고 결국 반비례하기 때문에 이동의 거의 사라지게 된다.

RMSPropOptimizer는 Adagradient descent의 단점을 보완한 알고리즘으로 변수가 이동한 gradient의 합이 아니라 지수평균으로 바꿔서 해당 단점을 보완한 알고리즘이다. 해당 알고리즘 역시 동일한 step size가 아닌 가변적인 step size를 적용하기 위해 도입된 알고리즘이다.

Autoencoder class를 보면 init 함수외에 get_batch 함수라는 것도 정의했다. 이 함수는 training시에 한 번에 하나씩 데이터를 집어넣어서 weight를 업데이트 하는 것이 아니라, 한 번에 여러 개의 데이터를 집어넣고 해당 loss의 평균으로 weight를 업데이트 하는 방식을 말한다. 이렇게 하면 보다 빠르게 training 시간을 완료할 수가 있다.

이 코드에서는 한 번에 10개씩 데이터를 training 하고 있다.

그리고 train 함수가 있다.

epoch만큼 train을 돌리는데, 한번에 batch_size만큼 가져온 후 weight를 update한다. epoch가 10 단위일 때마다 loss를 찍게 해놨다.

test 함수는 data를 입력받은 후, 해당 data를 입력으로 training 된 autoencoder 모델을 적용해서 나온 결과를 출력하도록 코딩했다.

위의 코드처럼 Autoencoder class를 생성한 후, train과 test를 실행해보자.