Self-Attention

NLP 글 목록

한빛미디어의 <밑바닥부터 시작하는 딥러닝 2>를 요약 정리한 글이다.

1. Attention에서 출발한 직관

일반 Attention은 다음 구조를 가진다.

  • 기준: 현재 시점의 hidden state hth_t
  • 참조: 전체 hidden states h1hnh_1 \sim h_n

질문은 하나이다.

현재 상태 hth_t가 전체 맥락 중 무엇을 얼마나 참고해야 하는가?

즉 일반 Attention은 이미 압축된 표현 hth_t가 전체 시퀀스를 다시 조회하는 구조이다.

seq2seq에서 이 구조는 Decoder의 현재 상태가 Encoder의 전체 hidden states를 참고하는 방식으로 나타난다.

Decoder가 어떤 단어를 생성하려는 시점마다 입력 문장의 어느 부분을 참고할지 attention weight로 결정한다.

2. Self-Attention의 관점 전환

Self-Attention은 전제를 바꾼다.

일반 Attention에서는 Decoder의 현재 hidden state가 기준이 되고, Encoder hidden states가 참조 대상이 된다.

반면 Self-Attention에서는 하나의 시퀀스 안에서 모든 토큰이 서로를 참조한다.

즉 문맥을 시간 누적의 결과로만 보지 않는다.

Self-Attention에서 문맥은 토큰 간 관계의 함수이다.

따라서 하나의 기준점만 둘 이유가 없다.

모든 토큰이 동시에 기준, 즉 Query가 된다.

각 토큰은 자기 관점에서 전체 문장을 다시 해석한다.

3. Self-Attention의 핵심 직관

Self-Attention은 모든 토큰 hih_i에 대해 다음 질문을 동시에 수행한다.

토큰 hih_i의 의미를 정할 때 다른 어떤 토큰 hjh_j들이 얼마나 중요한가?

그래서 Self-Attention에서는 토큰마다 서로 다른 문맥 가중치를 가진다.

또 입력 토큰 개수와 동일한 개수의 출력 벡터가 생성된다.

이는 전체 문장을 하나의 벡터로 압축하는 과정이 아니다.

각 토큰 표현을 문맥을 반영한 새 표현으로 업데이트하는 재표현(representation update) 과정이다.

4. 모든 hihjh_i \cdot h_j 계산이 가능한 이유

임베딩 또는 hidden vector는 의미 공간의 좌표이다.

두 벡터의 내적은 두 토큰이 의미적으로 얼마나 관련 있는지를 나타내는 유사도 측정으로 사용할 수 있다.

hihjh_i \cdot h_j

이 값은 다음 의미로 해석할 수 있다.

토큰 ii의 관점에서 토큰 jj가 의미적으로 얼마나 관련 있는가?

Self-Attention에는 RNN처럼 과거와 현재를 순서대로 누적하는 구조가 없다.

시간 순서에 따른 누적보다, 토큰 사이의 관계가 중심이 된다.

따라서 모든 쌍 (i,j)(i, j)에 대한 유사도를 계산할 수 있다.

이 계산을 통해 각 토큰은 문장 안의 모든 다른 토큰을 참고할 수 있다.

5. Q, K, V의 역할 분리

Self-Attention에서는 같은 입력 hh를 서로 다른 용도로 사용하기 위해 Query, Key, Value로 분리한다.

Query

Query는 “내가 무엇을 찾고 있는가”를 나타낸다.

관계 판단의 기준이 되는 벡터이다.

Key

Key는 “어떤 기준으로 비교될 수 있는가”를 나타낸다.

Query와의 유사도 계산에 사용된다.

Value

Value는 “선택되었을 때 실제로 전달될 정보”를 나타낸다.

attention weight를 곱해 가중합하는 대상이다.

요약하면 다음과 같다.

  • Q: 질문이다.
  • K: 비교 기준이다.
  • V: 전달 내용이다.

6. Q, K, V를 분리해야 하는 이유

관계 판단에 유용한 특징과 의미 전달에 유용한 특징은 다를 수 있다.

이를 분리하지 않으면 비교에 필요한 정보와 전달에 필요한 정보가 하나의 벡터에 섞여 충돌할 수 있다.

그래서 입력 hidden vector를 서로 다른 가중치로 투영한다.

Q=HWQ,K=HWK,V=HWVQ = H W_Q,\quad K = H W_K,\quad V = H W_V

여기서 WQW_Q, WKW_K, WVW_V는 학습 가능한 가중치 행렬이다.

이 투영을 통해 모델은 같은 입력 토큰을 질문용 표현, 비교용 표현, 전달용 표현으로 나누어 사용할 수 있다.

7. Self-Attention 수식 정리

입력 시퀀스의 hidden states를 다음과 같이 두자.

H=[h1,h2,,hn]Rn×dH = [h_1, h_2, \dots, h_n] \in \mathbb{R}^{n \times d}

여기서 nn은 토큰 수이고, dd는 hidden dimension이다.

먼저 Query, Key, Value를 만든다.

Q=HWQ,K=HWK,V=HWVQ = H W_Q,\quad K = H W_K,\quad V = H W_V

그 다음 Query와 Key의 내적으로 score를 계산한다.

S=QKS = QK^\top

보통 score를 dk\sqrt{d_k}로 나누어 scale을 조정한다.

A=softmax(QKdk)A = \mathrm{softmax} \left( \frac{QK^\top}{\sqrt{d_k}} \right)

여기서 AA는 attention weight matrix이다.

마지막으로 attention weight와 Value를 곱해 출력 표현을 만든다.

O=AVO = AV

각 행 OiO_i는 토큰 ii가 전체 토큰을 참고해 재계산한 문맥 반영 표현이다.

8. Self-Attention의 본질

Self-Attention의 본질은 다음과 같다.

  • 순환 구조가 아니다.
  • 과거 요약을 조회하지 않는다.
  • 토큰 간 관계로 표현을 재정의한다.

각 토큰은 같은 시퀀스의 모든 토큰을 참고한다.

그리고 자기 관점에서 문맥 표현을 얻는다.

즉 Self-Attention은 문장 전체를 한 번에 보고, 각 토큰의 의미를 문장 안의 다른 토큰들과의 관계 속에서 다시 계산하는 구조이다.

9. Multi-Head와의 연결

Single-Head Attention은 하나의 관계 공간에서 attention을 계산한다.

이 경우 여러 종류의 관계가 하나의 attention weight 안에 평균적으로 섞일 수 있다.

Multi-Head Attention은 여러 개의 독립된 Q/K/V 공간을 사용한다.

각 head는 서로 다른 관점의 관계를 병렬로 포착한다.

예를 들어 어떤 head는 주어와 동사의 관계를 보고, 다른 head는 지시어와 참조 대상을 볼 수 있다.

정리하면 다음과 같다.

  • Single-Head: 하나의 관계 공간을 사용한다.
  • Multi-Head: 여러 독립된 관계 공간을 병렬로 사용한다.

Multi-Head Attention은 표현 공간을 분리해 관계 표현력을 확장한 Self-Attention 구조이다.