본문 바로가기
Deep Learning

Normalization, Standardization, Initialization, optimization

by 자라자 2020. 8. 18.

미래연구소 홈페이지: https://futurelab.creatorlink.net/

Normalization

Normalization은 데이터의 전처리 과정 중 하나로, scale을 0에서 1 사이로 만들어 주는 작업이다. 데이터를 정규화해주는 작업은 학습속도를 향상시키고 local minimum에 빠지는 가능성을 줄인다. 또한 Gradient Descent를 더 편리하게 수행할 수 있도록 한다.

Normalization의 수식은 (요소값-최소값)/(최대값-최소값)이 된다. 즉, 해당 요소값이 최대값이라면 1이되고, 최소값이라면 0으로 바뀐다. sklearn에서 MinMaxScaler를 import해서 간단하게 구현할 수 있다.

 

 

1

2

3

4

 

 

# MinMaxScaler 구현하기

from sklearn.preprocessing import MinMaxScaler

mm = MinMaxScaler()

train_dataset=mm.fit_transform(train_dataset)

 

cs

 

 

Standardization

Standardization은 고등학교 때 배운 그 표준화이다. 데이터를 표준정규분포로 맞춰준다. feature 값에서 평균을 빼주고 표준편차로 나누어서 구현한다. sklearn에서 제공하는 dataset 중 iris에 관한 데이터로 구현을 해보자.

 

1

2

3

 

 

from sklearn.datasets import load_iris

iris=load_iris()

iris.data

 

cs

seaborn을 이용해 시각화를 해보면,

이러한 데이터임을 알 수 있다. standardization을 위해서 numpy로 평균과 표준편차를 구해준다. feature 중 sepal_width 를 표준화해보자.

 

1

2

3

 

 

import numpy as np

sepal_width=iris.data[:,1]

sepal_width_scaled=(sepal_width-np.mean(sepal_width))/np.std(sepal_width)

 

cs

이런 과정으로 진행할 수 있다. 이것보다 더 간단하게 구현할 수 있는데, Scikit-Learn의 fit_transform을 이용하면 된다.

 

 

 

Initialization

기존의 zero initialization에는 vanishing gradient와 symmetric row라는 문제점이 있었다. 그것을 개선하기 위해서 random initialization을 해주고, 0과 1로 값이 편향되지 않도록 0.01을 곱해서 분포를 조정했다. 그런데 random initialization에도 문제가 있다. fan-in 과 fan-out이 적절하지 않으면 레이어가 중첩됨에 따라 gradient vanishing이나 gradient exploding이 일어날 수 있다는 것이다. 아래 사진은 초기화 상수가 0.01일 때 표준편차가 0으로 점점 변하는 것을 보인다. 이는 vanishing gradient를 유발한다.

 

이는 0.01등의 초기화 상수를 0.05로 바꿔주어 해소할 수 있다.

initialization의 문제를 해소하기 위해서는 fan-in이 클수록 초기화 상수를 작게, fain-in이 클수록 초기화상수를 크게 설정하면 된다. 즉 반비례한 초기화상수를 이용하면 되는데, 이를 반영한 여러가지 initialization 기법이 있다. 그 중 이번 과제에 사용한 He Initialization은 다음과 같다.

 

실제 구현은 Sequential, Dense를 import한 후 kernel_initializer를 he normal로 구현하면 된다.

1
2
3
4
5
6
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import Dense
 
def create_model():
    model = Sequential()
    model.add(Dense(64, input_shape=(784,), activation = 'relu',kernel_initializer='he_normal'))

cs

이런 느낌으로 구현할 수 있다!

 

Optimization

데이터가 50000개이면 메모리상 50000개를 전부 띄울 수 없기 때문에 한 번에 계산을 하지 않는다. Batch는 전체 데이터, mini-batch는 일부(표본이라고 생각하면 편할듯 하다)를 뜻하는데, mini-batch로 나누어 여러번에 걸쳐 계산한다. 이를 optimiztion이라고 하고, mini-batch size는 hyper parameter이므로 사용자가 조절해주어야 한다. 

 

SGD는 확률적 경사하강법으로, random하게 추출한 minibatch로 경사하강법을 수행한다. 즉, 표본을 가지고 global minimum을 찾는다고 이해하면 편할 것이다. 

케라스 공식 홈페이지에 옵티마이저에 관한 전반적인 설명이 있다. 

https://keras.io/ko/optimizers/

 

Optimizers - Keras Documentation

옵티마이저의 사용법 옵티마이저는 Keras 모델을 컴파일하기 위해 필요한 두 개의 매개변수(parameter) 중 하나입니다. from keras import optimizers model = Sequential() model.add(Dense(64, kernel_initializer='uniform', inp

keras.io

그러나 이렇게 진행하면 두 가지 문제가 있는데, 하나는 dimension별로 gradient 차이가 클 경우 계산시간이 과도하게 길어질 수 있다는 점이고, 다른 하나는 local minimum에 갇힐 수 있다는 점이다.

 

이를 극복하기 위해 learning rate에 관성을 부여한다. 다양한 기법이 있는데 보통은 adam을 쓴다.

 

그림 출처: 미래연구소 학습자료