RNN의 은닉 상태 구조와 장기 의존성 문제
순환 신경망의 은닉 상태·피드백 루프 구조와 장기 의존성·기울기 소실 문제, 트랜스포머로 이어지는 흐름을 정리한다.
2026-08-13 · 최초 발행 2025-05-23
문장을 읽을 때 우리는 앞 단어를 기억한 채로 다음 단어를 이해한다. 순환 신경망(RNN)은 이 순서 감각을 신경망 구조로 옮긴 것이다. 내부 메모리로 이전 입력의 정보를 유지하고 현재 계산에 반영하는 방식으로 텍스트, 음성, 시계열 데이터 같은 순차적 정보를 처리하며, 자연어 처리(NLP), 음성 인식, 기계 번역 등에서 쓰인다.
은닉 상태와 피드백 루프
순환 신경망의 핵심은 '순환' 개념이다. 일반적인 전방향(feedforward) 신경망과 달리 RNN은 네트워크의 출력이 다시 입력으로 들어가는 피드백 루프를 포함한다.
은닉 상태(hidden state)는 네트워크의 '메모리'로 작용하며, 시퀀스의 각 요소는 타임스텝(time step)별로 순차적으로 처리된다. 모든 타임스텝에는 동일한 가중치가 공유된다.
기본적인 RNN의 수학적 표현은 다음과 같다.
- 현재 은닉 상태: h*t = tanh(W_hx * x_t + W_hh _ h_{t-1} + b_h)
- 출력: y_t = W_hy * h_t + b_y
여기서 x_t는 현재 입력, h_t는 현재 은닉 상태, h_{t-1}은 이전 은닉 상태, y_t는 현재 출력이며, W_hx·W_hh·W_hy는 가중치 행렬, b_h·b_y는 편향(bias) 벡터다.
순환 구조의 변형들
기본 RNN(Vanilla RNN)은 가장 단순한 형태로, 장기 의존성 문제(long-term dependency problem)를 안고 있고 기울기 소실/폭발 문제(vanishing/exploding gradient problem)에도 취약하다.
이 문제를 완화하려고 게이트 구조를 도입한 대표적 변형이 LSTM과 GRU다. LSTM은 셀 상태(cell state)와 망각·입력·출력 세 개의 게이트로 정보 흐름을 제어해 장기 메모리를 유지하고, GRU는 이를 리셋·업데이트 두 게이트로 단순화해 더 적은 매개변수로 LSTM과 유사한 성능을 낸다.
시퀀스를 정방향과 역방향으로 동시에 처리하는 양방향 RNN(Bidirectional RNN)도 있다. 두 방향의 정보를 모두 활용해 더 완전한 컨텍스트를 캡처하며, 자연어 처리에서 특히 유용하다.
자연어부터 시계열까지, RNN이 쓰이는 곳
자연어 처리(NLP)에서는 다음 단어·문자를 예측하는 텍스트 생성, 텍스트의 감정을 분류하는 감정 분석, 소스 언어에서 대상 언어로 옮기는 기계 번역, 자연어 질문에 응답하는 질의응답 시스템에 활용된다. 구글의 BERT(Bidirectional Encoder Representations from Transformers)는 양방향 학습을 활용하며, RNN의 개념을 확장한 트랜스포머 아키텍처를 사용해 다양한 NLP 작업에서 최고 성능을 달성한 사례다.
음성 인식과 처리에서는 오디오 입력을 텍스트로 바꾸는 음성-텍스트 변환(STT), 음성 패턴 기반의 화자 식별에 쓰인다. 애플 Siri, 구글 어시스턴트, 아마존 알렉사 같은 음성 비서 시스템이 RNN과 그 변형으로 음성 명령을 처리한다.
시계열 예측에서는 과거 주가 데이터로 미래 가격을 예측하거나, 기상 데이터 시계열로 날씨를 예보하거나, 과거 사용 패턴으로 전력 수요를 예측하는 데 쓰인다. 전력 회사들은 LSTM 기반 모델로 일일 전력 수요를 예측해 자원 할당을 최적화하고 비용을 절감한다.
비디오 분석에서는 비디오 프레임 시퀀스에서 인간 행동 패턴을 식별하는 행동 인식, 비디오 콘텐츠를 설명하는 비디오 캡셔닝에 쓰인다. 비디오 감시 시스템은 RNN 기반 모델로 이상 행동을 실시간으로 감지하고 경고한다.
장기 의존성과 기울기 소실이라는 근본 한계
기본 RNN은 장거리 의존성을 효과적으로 모델링하지 못한다. LSTM, GRU 같은 변형이 이 문제를 완화하지만 완전히 해결하지는 못한다.
역전파 과정에서는 그래디언트가 시간이 지남에 따라 너무 작아지거나(소실) 너무 커질(폭발) 수 있다. 기울기 클리핑, 가중치 정규화, 적절한 활성화 함수 선택이 해결책으로 쓰인다.
RNN의 순차적 특성은 병렬 처리를 제한한다. 이 한계를 극복하기 위해 개발된 것이 트랜스포머(Transformer) 아키텍처다.
어텐션과 트랜스포머로 이어지는 흐름
RNN의 성능을 개선하기 위해 도입된 어텐션 메커니즘(Attention Mechanism)은 모델이 입력 시퀀스의 특정 부분에 집중할 수 있게 하며, 기계 번역과 이미지 캡셔닝에서 큰 성공을 거뒀다.
트랜스포머(Transformer) 아키텍처는 어텐션 메커니즘만으로 RNN의 순차적 처리 한계를 극복한다. 병렬 처리가 가능하고 장기 의존성 문제도 완화되며, BERT·GPT 같은 최신 NLP 모델의 기반이 됐다.
RNN과 CNN을 결합하거나, RNN과 트랜스포머의 장점을 결합하는 하이브리드 모델 연구도 특정 태스크에 최적화된 아키텍처 설계 방향으로 이어지고 있다.
PyTorch로 구현하는 기본 RNN
import torch
import torch.nn as nn
class SimpleRNN(nn.Module):
def __init__(self, input_size, hidden_size, output_size):
super(SimpleRNN, self).__init__()
self.hidden_size = hidden_size
self.rnn = nn.RNN(input_size, hidden_size, batch_first=True)
self.fc = nn.Linear(hidden_size, output_size)
def forward(self, x):
# x shape: (batch_size, sequence_length, input_size)
h0 = torch.zeros(1, x.size(0), self.hidden_size).to(x.device)
out, _ = self.rnn(x, h0)
# 마지막 타임스텝의 출력만 사용
out = self.fc(out[:, -1, :])
return out
# 모델 초기화
input_size = 10 # 입력 크기
hidden_size = 20 # 은닉층 크기
output_size = 5 # 출력 크기
model = SimpleRNN(input_size, hidden_size, output_size)
# 입력 데이터 예시
batch_size = 3
seq_length = 5
sample_input = torch.randn(batch_size, seq_length, input_size)
# 모델 실행
output = model(sample_input)
print(output.shape) # torch.Size([3, 5])