본문 바로가기

인공지능/딥러닝

[딥러닝DL] 순환신경망(RNN) - 장기기억 순환신경망(LSTM), 게이트웨이 반복 순환신경망(GRU)

~ 목차 ~

순환신경망  🐸

 

순환신경망(Recurrent Neural Network, RNN)

 - RNN은 텍스트 처리를 위해 고안된 모델(계층)
 - 바로 이전의 데이터(텍스트)를 재사용하는 신경망 계층임 (이전의 기억을 가지고 있다☆)
   EX) 챗봇, 은행 카카오톡 서비스

 

순환신경망 종류

 - 심플 순환신경망(Simple RNN)
 - 장기기억 순환신경망(LSTM)
 - 게이트웨이 반복 순환신경망(GRU)

 

simple RNN 단점

- 긴 문장(시퀀스)을 학습하기 어려움
- 시퀀스가 길 수록 초반의 정보는 점진적으로 희석(소멸) 됨
  즉, 멀리 떨어져 있는 단어의 정보를 인식하는데 어려움이 있음
- 이러한 단점을 보완한 모델이 LSTM과 GRU

 

LSTM(Long Short-Term Memory, 장기기억)

- 단기기억을 오래 기억할 수 있도록 고안된 모델
- 많은 이전 정보를 기억해야 하기 때문에 훈련 속도가 느리며, 시스템 저장 공간이 많이 필요함

 

GRU(Gated Recurrent Unit, 게이트 반복 단위)

- LSTM의 느린 속도를 개선하기 위해 고안된 모델
- 성능은 LSTM과 유사함

 

** Simple RNN, LSTM, GRU 모두 RMSprop 옵티마이저를 일반적으로 사용함

 

 

순환신경망 - LSTM  🐸

 

라이브러리

import tensorflow as tf
from tensorflow import keras
from sklearn.model_selection import train_test_split

"""영화 감상평에 대한 긍정/부정 데이터셋"""
from tensorflow.keras.datasets import imdb

"""텍스트 길이 정규화 라이브러리"""
from tensorflow.keras.preprocessing.sequence import pad_sequences

 

 

사용할 데이터 : IMDB

 

데이터 불러들이기

- IMDB 데이터 사용, 말뭉치 500개 사용

(train_input, train_target), (test_input, test_target) = imdb.load_data(num_words=500)

print(train_input.shape, train_target.shape)
print(test_input.shape, test_target.shape)

 

(25000,) (25000,)
(25000,) (25000,)

 

 

훈련 : 검증데이터로 분류하기, 8:2

 

데이터 분류하기

- train : val = 8 : 2로 분류하기

train_input, val_input, train_target, val_target = train_test_split(train_input, train_target,
                                                                    test_size=0.2,
                                                                    random_state=42)
print(train_input.shape, train_target.shape)
print(val_input.shape, val_target.shape)
print(test_input.shape, test_target.shape)

 

(20000,) (20000,)
(5000,) (5000,)
(25000,) (25000,)

 

 

 

텍스트 정규화하기

 

텍스트 정규화하기

- 훈련, 검증, 테스트 데이터 내에 각 문장의 길이를 100으로 통일(정규화) 시키기
- 앞쪽을 제거, 앞쪽을 채우기
why? 훈련은 행렬 데이터로 이루어지기 때문에 사이즈를 맞춰서 진행해야함(비어있는 값이 없이)

train_seq = pad_sequences(train_input, maxlen=100)

val_seq = pad_sequences(val_input, maxlen=100)

test_seq = pad_sequences(test_input, maxlen=100)

print(train_seq.shape, train_target.shape)
print(val_seq.shape, val_target.shape)
print(test_seq.shape, test_target.shape)

 

(20000, 100) (20000,)
(5000, 100) (5000,)
(25000, 100) (25000,)

 

 

LSTM 모델 훈련

 

모델 생성하기

model = keras.Sequential()
model

 

 

 

계층 생성 및 모델에 추가하기

- 임베딩 계층 추가 : 말뭉치 500, 출력크기 16, 입력크기 100
- LSTM 계층 추가 : 출력크기 8
- 출력 계층 추가 

model.add(
    keras.layers.Embedding(500, 16, input_length=100)
)
model.add(
    keras.layers.LSTM(8)
)
model.add(
    keras.layers.Dense(1, activation="sigmoid")
)
model.summary()

 

 

 

 

 

 

모델 설정하기

- 옵티마이저 : RMSprop, 학습율 : 0.0001

rmsprop = keras.optimizers.RMSprop(learning_rate=0.0001)
model.compile(optimizer=rmsprop, loss="binary_crossentropy", metrics=["accuracy"])

 

 

콜백 함수 정의하기

- 자동 저장 위치 및 파일명 : ./model/best_LSTM_model.h5

checkpoint_cb = keras.callbacks.ModelCheckpoint("./model/best_LSTM_model.h5")
early_cb = keras.callbacks.EarlyStopping(patience=3, restore_best_weights=True)

checkpoint_cb, early_cb

 

 

모델 훈련시키기

- 100번 반복, 배치사이즈 64, 검증 동시 진행

history=model.fit(train_seq, train_target ,epochs=100, batch_size=64, 
                           validation_data=(val_seq, val_target), callbacks=[checkpoint_cb,early_cb])

 

LSTM 모델 성능 검증 

 

훈련, 검증, 테스트 성능 검증하기

train_eval = model.evaluate(train_seq, train_target)
val_eval = model.evaluate(val_seq, val_target)
test_eval = model.evaluate(test_seq, test_target)

 

625/625 [==============================] - 3s 4ms/step - loss: 0.4119 - accuracy: 0.8140
157/157 [==============================] - 1s 4ms/step - loss: 0.4358 - accuracy: 0.7982
782/782 [==============================] - 3s 3ms/step - loss: 0.4304 - accuracy: 0.8018

 


 

순환신경망 - LSTM(드롭아웃, Dropout) 🐸

 

LSTM 모델에 드롭아웃 속성(계층 아님) 적용하기

- LSTM 모델(계층)에 드롭아웃 속성 적용, 30% 훈련에서 제외
- 나머지 모두 위와 동일하게 처리하여 훈련, 검증, 테스트 데이터에 대한 성능검증까지 진행하기

 

LSTM 모델(드롭아웃) 훈련

"""모델 생성하기"""
model = keras.Sequential()


"""계층 생성 및 모델에 추가하기
- 임베딩 계층 추가 : 말뭉치 500, 출력크기 16, 입력크기 100
- LSTM 계층 추가 : 출력크기 8
- 출력 계층 추가 
"""
model.add(keras.layers.Embedding(500, 16, input_length=100))
model.add(keras.layers.LSTM(8, dropout=0.3))
model.add(keras.layers.Dense(1, activation="sigmoid"))

"""모델 설정하기
- 옵티마이저 : RMSprop, 학습율 : 0.0001
"""
rmsprop = keras.optimizers.RMSprop(learning_rate=0.0001)
model.compile(optimizer=rmsprop, loss="binary_crossentropy", metrics=["accuracy"])

"""콜백 함수 정의하기
- 자동 저장 위치 및 파일명 : ./model/best_LSTM_model.h5
"""
checkpoint_cb = keras.callbacks.ModelCheckpoint("./model/best_LSTM_model.h5")
early_cb = keras.callbacks.EarlyStopping(patience=3, restore_best_weights=True)

"""모델 훈련시키기
- 100번 반복, 배치사이즈 64, 검증 동시 진행
"""
history=model.fit(train_seq, train_target ,epochs=100, batch_size=64, validation_data=(val_seq, val_target), callbacks=[checkpoint_cb,early_cb])

 

 

LSTM 모델(드롭아웃) 성능 검증 

 

훈련, 검증, 테스트 성능 검증하기

 

train_eval = model.evaluate(train_seq, train_target)
val_eval = model.evaluate(val_seq, val_target)
test_eval = model.evaluate(test_seq, test_target)

 

625/625 [==============================] - 3s 4ms/step - loss: 0.4082 - accuracy: 0.8149
157/157 [==============================] - 1s 4ms/step - loss: 0.4318 - accuracy: 0.7978
782/782 [==============================] - 3s 4ms/step - loss: 0.4290 - accuracy: 0.8015

 

 


 

 

 

순환신경망 - LSTM(2개 연결하기) 🐸

 

LSTM 모델 2개 연결하기

- LSTM 2개를 연결할 때는 연속해서 LSTM 계층을 추가해야함
- 첫번째 LSTM 계층의 속성에는 return_sequences=True 속성을 추가해 줍니다.
- 두번째 LSTM은 첫번째 LSTM의 훈련결과를 이어받아서 계속 훈련을 이어나갑니다.

 

LSTM 모델(드롭아웃) 훈련

"""모델 생성하기"""
model = keras.Sequential()


"""계층 생성 및 모델에 추가하기
- 임베딩 계층 추가 : 말뭉치 500, 출력크기 16, 입력크기 100
- LSTM 계층 추가 : 출력크기 8
- 출력 계층 추가 
"""
model.add(keras.layers.Embedding(500, 16, input_length=100))
model.add(keras.layers.LSTM(8, dropout=0.3, return_sequences=True))
model.add(keras.layers.LSTM(8, dropout=0.2))
model.add(keras.layers.Dense(1, activation="sigmoid"))

"""모델 설정하기
- 옵티마이저 : RMSprop, 학습율 : 0.0001
"""
rmsprop = keras.optimizers.RMSprop(learning_rate=0.0001)
model.compile(optimizer=rmsprop, loss="binary_crossentropy", metrics=["accuracy"])

"""콜백 함수 정의하기
- 자동 저장 위치 및 파일명 : ./model/best_LSTM_model.h5
"""
checkpoint_cb = keras.callbacks.ModelCheckpoint("./model/best_LSTM_model.h5")
early_cb = keras.callbacks.EarlyStopping(patience=3, restore_best_weights=True)

"""모델 훈련시키기
- 100번 반복, 배치사이즈 64, 검증 동시 진행
"""
history=model.fit(train_seq, train_target ,epochs=100, batch_size=64, validation_data=(val_seq, val_target), callbacks=[checkpoint_cb,early_cb])

 

 

LSTM 모델(드롭아웃) 성능 검증 

 

훈련, 검증, 테스트 성능 검증하기

 

train_eval = model.evaluate(train_seq, train_target)
val_eval = model.evaluate(val_seq, val_target)
test_eval = model.evaluate(test_seq, test_target)

 

625/625 [==============================] - 5s 7ms/step - loss: 0.4132 - accuracy: 0.8127
157/157 [==============================] - 1s 6ms/step - loss: 0.4354 - accuracy: 0.7966
782/782 [==============================] - 5s 6ms/step - loss: 0.4304 - accuracy: 0.7979

 

 

 


 

 

 

순환신경망 - GRU 모델 🐸

 

LSTM 모델 2개 연결하기

- LSTM 2개를 연결할 때는 연속해서 LSTM 계층을 추가해야함
- 첫번째 LSTM 계층의 속성에는 return_sequences=True 속성을 추가해 줍니다.
- 두번째 LSTM은 첫번째 LSTM의 훈련결과를 이어받아서 계속 훈련을 이어나갑니다.

 

GRU 모델 훈련

"""모델 생성하기"""
model = keras.Sequential()


"""계층 생성 및 모델에 추가하기
- 임베딩 계층 추가 : 말뭉치 500, 출력크기 16, 입력크기 100
- GRU 계층 추가 : 출력크기 8
- 출력 계층 추가 
"""
model.add(keras.layers.Embedding(500, 16, input_length=100))
model.add(keras.layers.GRU(8))
model.add(keras.layers.Dense(1, activation="sigmoid"))

"""모델 설정하기
- 옵티마이저 : RMSprop, 학습율 : 0.0001
"""
rmsprop = keras.optimizers.RMSprop(learning_rate=0.0001)
model.compile(optimizer=rmsprop, loss="binary_crossentropy", metrics=["accuracy"])

"""콜백 함수 정의하기
- 자동 저장 위치 및 파일명 : ./model/best_GRU_model.h5
"""
checkpoint_cb = keras.callbacks.ModelCheckpoint("./model/best_GRU_model.h5")
early_cb = keras.callbacks.EarlyStopping(patience=3, restore_best_weights=True)

"""모델 훈련시키기
- 100번 반복, 배치사이즈 64, 검증 동시 진행
"""
history=model.fit(train_seq, train_target ,epochs=100, batch_size=64, validation_data=(val_seq, val_target), callbacks=[checkpoint_cb,early_cb])

 

 

GRU 모델 성능 검증 

 

훈련, 검증, 테스트 성능 검증하기

 

train_eval = model.evaluate(train_seq, train_target)
val_eval = model.evaluate(val_seq, val_target)
test_eval = model.evaluate(test_seq, test_target)

 

625/625 [==============================] - 2s 3ms/step - loss: 0.4019 - accuracy: 0.8202
157/157 [==============================] - 1s 3ms/step - loss: 0.4308 - accuracy: 0.8022
782/782 [==============================] - 2s 3ms/step - loss: 0.4259 - accuracy: 0.8007

 

 

728x90