IMDB 영화 리뷰 데이터셋을 사요하여 다양한 순환 신경망(RNN) 아키텍처의 성능을 감성 분석에 대해 알아본다. LSTM 및 GRU 층을 사용하고, 드롭아웃을 적용하여 규제화하여, 여러 층을 쌓아보도록 한다.
from tensorflow.keras.datasets import imdb
from sklearn.model_selection import train_test_split
# 단어 수를 500개로 제한하여 데이터 로드
(train_input, train_target), (test_input, test_target) = imdb.load_data(num_words=500)
# 훈련 데이터를 훈련 세트와 검증 세트로 분리
train_input, val_input, train_target, val_target = train_test_split(train_input, train_target, test_size=0.2, random_state=42)
from tensorflow.keras.preprocessing.sequence import pad_sequences
# 데이터를 패딩하여 길이를 100으로 맞춤
train_seq = pad_sequences(train_input, maxlen=100)
test_seq = pad_sequences(test_input, maxlen=100)
val_seq = pad_sequences(val_input, maxlen=100)
단일 LSTM 층과 시그모이드 활성화 함수를 사용하는 밀집 층으로 구성된 간단한 LSTM 모델
from tensorflow import keras
# LSTM 모델 구축
model = keras.Sequential()
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 = keras.optimizers.RMSprop(learning_rate=1e-4)
model.compile(optimizer=rmsprop, loss='binary_crossentropy', metrics=['accuracy'])
# 콜백 설정
checkpoint_cb = keras.callbacks.ModelCheckpoint('best-lstm-model.keras', save_best_only=True)
early_stopping_cb = keras.callbacks.EarlyStopping(patience=3, restore_best_weights=True)
# 모델 훈련
history = model.fit(train_seq, train_target, epochs=100, batch_size=64, validation_data=(val_seq, val_target), callbacks=[checkpoint_cb, early_stopping_cb])
기본 순환층보다 LSTM이 과대적합을 억제하면서 훈련

과적합을 방지하기 위해 LSTM층에 드롭아웃을 추가
# 드롭아웃을 적용한 LSTM 모델 구축
# 드롭아웃을 적용한 LSTM 모델 구축
model2 = keras.Sequential()
model2.add(keras.layers.Embedding(500, 16, input_length=100))
model2.add(keras.layers.LSTM(8, dropout=0.3))
model2.add(keras.layers.Dense(1, activation='sigmoid'))
# 모델 컴파일
model2.compile(optimizer=rmsprop, loss='binary_crossentropy', metrics=['accuracy'])
# 콜백 설정
checkpoint_cb = keras.callbacks.ModelCheckpoint('best-dropout-model.keras', save_best_only=True)
early_stopping_cb = keras.callbacks.EarlyStopping(patience=3, restore_best_weights=True)
# 모델 훈련
history2 = model2.fit(train_seq, train_target, epochs=100, batch_size=64, validation_data=(val_seq, val_target), callbacks=[checkpoint_cb, early_stopping_cb])
훈련손실과 검증 손실간의 차이가 줄어듦

두 개의 LSTM 층을 쌓아 더 깊은 모델을 만들어 성능을 향상시킬 수 있는지 확인
# 다중 LSTM 층을 쌓은 모델 구축
model3 = keras.Sequential()
model3.add(keras.layers.Embedding(500, 16, input_length=100))
model3.add(keras.layers.LSTM(8, dropout=0.3, return_sequences=True))
model3.add(keras.layers.LSTM(8, dropout=0.3))
model3.add(keras.layers.Dense(1, activation='sigmoid'))
# 모델 컴파일
model3.compile(optimizer=rmsprop, loss='binary_crossentropy', metrics=['accuracy'])
# 콜백 설정
checkpoint_cb = keras.callbacks.ModelCheckpoint('best-stacked-lstm-model.keras', save_best_only=True)
early_stopping_cb = keras.callbacks.EarlyStopping(patience=3, restore_best_weights=True)
# 모델 훈련
history3 = model3.fit(train_seq, train_target, epochs=100, batch_size=64, validation_data=(val_seq, val_target), callbacks=[checkpoint_cb, early_stopping_cb])
과대적합 잘 제어되었음

GRU 층을 사용하여 LSTM보다 계산 효율이 높은 모델을 확인
# GRU 모델 구축
model4 = keras.Sequential()
model4.add(keras.layers.Embedding(500, 16, input_length=100))
model4.add(keras.layers.GRU(8))
model4.add(keras.layers.Dense(1, activation='sigmoid'))
# 모델 컴파일
model4.compile(optimizer=rmsprop, loss='binary_crossentropy', metrics=['accuracy'])
# 콜백 설정
checkpoint_cb = keras.callbacks.ModelCheckpoint('best-gru-model.keras', save_best_only=True)
early_stopping_cb = keras.callbacks.EarlyStopping(patience=3, restore_best_weights=True)
# 모델 훈련
history4 = model4.fit(train_seq, train_target, epochs=100, batch_size=64, validation_data=(val_seq, val_target), callbacks=[checkpoint_cb, early_stopping_cb])

✔️ 주요 포인트
- LSTM 구조
LSTM에는 은닉 상태와 셀 상태의 두 가지 순환 상태가 있다. 셀 상태는 주로 장기 메모리를 담당한다.
- GRU 구조
GRU는 LSTM보다 파라미터가 적어 계산이 빠르지만, 비슷한 성능을 보인다.