심층신경망(DNN)


💡 Deep Neural Network

심층 신경망(Deep Neural Network, DNN)은 입력층과 출력층 사이에 여러 개의

은닉층들로 이뤄진 인공신경망(Artificial Neural Network, ANN)이다.



💡 Flatten Layer

패션 MNIST 데이터는 28*28 크기이기 때문에 인공 신경망에 주입하기 위해

넘파이 배열의 reshape() 메서드를 사용해 1차원으로 펼쳐주었다.

물론 직접 1차원으로 펼처도 좋지만, keras에서는 이를 위한 Flatten Layer를 제공해준다.

Flatten 클래스는 배치 차원을 제외하고 나머지 입력 차원을 모두 일렬로 펼치는

역할만 할 뿐, 입력에 곱해지는 가중치나 절편이 없다.

따라서 인공 신경망의 성능을 위해 기여하는 바는 없다. 하지만 Flatten 클래스를

층처럼 입력층과 은닉층 사이에 추가하기 때문에 이를 층이라고 한다.



💡 Optimizer

신경망 학습의 목적은 손실 함수의 값을 가능한 한 낮추는 매개변수를 찾는 것이다.

이는 곧 매개변수의 최적값을 찾는 문제다.

이러한 문제를 풀기 위해 keras에서는 다양한 종류의 경사 하강법 알고리즘을 제공하는데

이를 Optimizer라고 한다.


확률적 경사 하강법(Stochastic Gradient Descent, SGD)

가장 기본적인 옵티마이저이다. 매 스텝에서 딱 한 개의 샘플을 무작위로 선택하고

그 하나의 샘플에 대한 그래디언트를 계산한다.

매 반복에서 매우 적은 데이터만 처리하기 때문에 알고리즘이 확실히 빠르게 돌아간다.


또한 매 반복에서 하나의 샘플만 메모리에 있으면 되므로 매우 큰 훈련 세트도

훈련 시킬 수 있다. 비용 함수가 최솟값에 다다를 때까지 부드럽게 감소하지 않고

위아래로 요동치면서 평균적으로 감소한다.(지그재그가 굉장히 크다)

시간이 지나면서 최솟값에 매우 근접하지만 요동이 지속되면서 최솟값에 안착하진 못한다.


물론 알고리즘이 멈출 때 좋은 파라미터가 구해지겠지만 최적치라고 장담할 수는 없다.

무작위성은 지역 최소 값에서 탈출 시켜줘서 좋지만 알고리즘을 전역 최솟값에 다다르지

못하게 한다는 점에서는 좋지않다.

이 문제를 해결하는 방법에는 학습률을 점진적으로 감소시키는 방법들이 있다.


모멘텀

경사 하강법은 경사면을 따라 일정한 크기의 스텝으로 조금씩 내려간다.

반대로 모멘텀 최적화는 경사를 굴러가는 볼링공과 같다.

즉 처음에는 느리게 출발하지만, 시간이 지날수록 빠르게 가속되어 결과적으로 더 빠르다.

모멘텀 최적화는 경사 하강법과 반대로 이전 그레디언트가 얼마였는지가 중요하다.

매 반복에서 그레디언트 학습률을 구하여 가중치를 갱신하게 된다.

결과적으로 SGD보다 지그재그의 정도가 적어지는 것을 알 수 있다.


AdaGrad (Adaptive Gradient)

이 기법은 각각의 매개변수에 적응적으로 Adaptive 학습률 Learning rate을 조정하며

학습을 진행한다. 신경망 학습에서는 학습률 값이 굉장히 중요하다.

값이 너무 작으면 학습 시간이 너무 길어지고, 반대로 너무 크면 발산하여 학습이 제대로

이뤄지지 않는다. 학습률의 이런 특성 때문에 보통 처음에는 학습률이 크게 잡다가

학습률을 점차 줄여서 학습한다. 여기서 학습률을 서서히 낮추는 가장 간단한 방법은

매개변수 ‘전체’의 학습률 값을 일괄적으로 낮추는 것이다. 이를 더욱 발전시킨 것이

바로 AdaGrad이다. AdaGrad는 개별 매개변수에 맞춤형 값을 만들어준다.

AdaGrad는 과거의 기울기를 제곱하여 계속 더해가기 때문에 학습을 진행할수록

갱신 강도가 약해진다. 무한히 계속 학습할 경우에는 어느 순간 갱신량이 0이 되어

전혀 갱신되지 않게 된다. 이 문제를 개선한 기법으로 RMSProp이라는 방법이 있다.


RMSprop

RMSProp 알고리즘은 AdaGrad가 너무 빠르게 느려져서 전역 최적점에

수렴하지 못하는 문제를 가장 최근 반복에서 비롯된 그래디언트만 누적함으로써

해결한다.

또한 아주 간단한 문제를 제외하고는 이 옵티마이져가 AdaGrad보다 훨씬 더 성능이 좋다.

또 일반적으로 모멘텀 최적화나 네스트테로프 가속 경사보다 더 빠르게 수렴합니다.


Adam

‘모멘텀 최적화’와 ‘RMSprop’의 장점을 접목한 것이 Adam이다.

Adam은 RMSprop과 함께 맨 처음 시도해 볼 수 있는 좋은 알고리즘이다.

adaptive learning rate를 사용하는 이 3개(Adagrad, RMSprop, Adam)의 클래스는

learning_rate 매개변수의 default 값으로 모두 0.001을 사용한다



💡 적응적 학습률(adaptive learning rate)

모델이 최적점에 가까이 갈수록 학습률을 낮출 수 있다. 이렇게 하면 안정적으로

최적점에 수렴할 가능성인 높다. 이런 학습률을 적응적 학습률이라고 한다.

이런 방식들은 ‘학습률 매개변수’를 튜닝하는 수고를 덜 수 있는 것이 장점이다.

적응적 학습률을 사용하는 대표적인 옵티마이저는 Adagrad(디폴트 값)와 RMSprop이다.

각각 compile() 메서드의 optimizer 매개변수에 ‘adagrad’와 ‘rmsprop’로 지정 가능하다.



💡 Optimizer와 Flatten Layer를 사용한 모델링

데이터 불러오기 및 train/val 분리

# MNIST 데이터 가져오기
(train_input, train_target),(test_input,test_target) = keras.datasets.fashion_mnist.load_data()

# 0과 1사이의 값으로 정규화
train_scaled = train_input / 255

# 차원 축소 생략 → 모델링에서 Flatten layer 추가

# train / validation 분리
train_scaled, val_scaled, train_target, val_target = train_test_split(
    train_scaled, train_target, test_size=0.2, random_state=42
)


모델 생성

model = keras.Sequential()

# Flatten layer
model.add(keras.layers.Flatten(input_shape=(28,28)))

# 은닉층 
model.add(keras.layers.Dense(100, activation='relu'))

# 출력층
model.add(keras.layers.Dense(10, activation='softmax'))


Optimizer(Adam) 적용

# 컴파일
model.compile(
    optimizer='adam',
    loss='sparse_categorical_crossentropy',
    metrics='accuracy'
    )

# 모델 학습
model.fit(train_scaled,train_target, epochs=5)

# val 예측
model.evaluate(val_scaled,val_target)