트랜스포머와 Attention의 운영 직관
트랜스포머의 핵심인 self-attention이 어떻게 토큰 관계를 계산하는지 설명하고, 현대 LLM에서 KV cache, FlashAttention, long-context 최적화가 왜 비용과 성능의 중심이 되는지 정리한다.
Script Companion
오디오와 함께 스크립트 보기
- 01
트랜스포머를 이해하는 일은 현대 LLM의 비용과 성능을 이해하는 일에 가깝다. GPT, LLaMA, Claude, Gemini는 모두 decoder-only transformer 구조를 표준처럼 사용한다. 특히 long-context가 왜 비싼지, input 토큰과 output 토큰의 비용 차이가 왜 생기는지, KV cache 메모리가 왜 운영의 병목이 되는지에 대한 답이 attention 구조 안에 들어 있다.
- 02
Attention은 RNN과 LSTM이 갖던 한계를 밀어내며 등장했다. RNN 계열은 토큰을 한 개씩 순차 처리하기 때문에 GPU 병렬화가 어렵고, 멀리 떨어진 토큰 사이의 정보 전달도 약해지기 쉽다. 또한 하나의 hidden state에 과거 전체를 압축해야 하므로 state bottleneck이 생긴다. Attention is All You Need는 RNN을 버리고 attention만으로 모든 토큰을 직접 연결할 수 있음을 보였다.
- 03
Self-attention의 핵심은 각 토큰이 다른 모든 토큰을 얼마나 참고할지 동적으로 계산하는 것이다. Query와 Key의 내적, 즉 Q K^T는 모든 토큰 쌍의 유사도 행렬을 만든다. 여기에 √d_k로 나누는 분산 정규화를 적용해 softmax가 쉽게 포화되지 않게 하고, 행별 softmax로 attention weight를 만든다. 마지막으로 이 weight를 Value에 곱하면 각 토큰에 필요한 정보가 섞인다.
- 04
Multi-head attention은 attention을 여러 개의 작은 head로 나누어 병렬 계산한다. 각 head는 구문, 의미, 거리 같은 서로 다른 관계를 학습할 수 있다. 운영 관점에서는 query head와 KV head 수가 다를 수 있다는 점이 중요하다. LLaMA-3-8B는 num_heads 32, num_kv_heads 8, d_head 128이며, GQA 때문에 KV cache는 query head 32가 아니라 num_kv_heads 8 기준으로 계산해야 한다.
- 05
Self-attention 자체는 토큰의 순서를 모른다. 그래서 위치 정보를 별도로 넣어야 하며, 방식에는 Sinusoidal, Learned positional, RoPE, ALiBi, NoPE가 있다. 현대 LLM에서는 RoPE가 표준에 가깝다. RoPE는 회전 행렬을 Query와 Key에 적용해 상대 위치를 자연스럽게 표현하고, 추가 파라미터가 없으며 long-context 외삽에 강하다. Llama 3.1의 128K context도 RoPE 변형을 사용한다.
- 06
하나의 LLM layer는 attention만으로 끝나지 않는다. 현대 transformer block은 보통 pre-norm, residual connection, FFN이 함께 쌓이는 구조다. 정규화는 LayerNorm이나 RMSNorm을 쓰며, LLaMA, Mistral, Qwen, DeepSeek에서는 RMSNorm이 표준처럼 쓰인다. FFN은 대개 hidden_dim에서 4배 크기로 확장했다가 다시 줄이고, 활성화는 SwiGLU나 GELU를 사용한다. 이 layer가 LLaMA-3-8B에서는 32개, 70B에서는 80개 쌓인다.
- 07
LLM 표준이 decoder-only인 이유는 causal mask와 next-token prediction에 있다. Encoder-only는 BERT처럼 양방향 attention을 쓰고, Encoder-Decoder는 T5나 BART처럼 encoder와 decoder를 나눈다. 반면 GPT, LLaMA, Claude 같은 decoder-only 모델은 미래 토큰을 보면 안 되므로 attention 행렬의 상삼각을 -inf로 마스킹한다. 그러면 softmax 뒤 미래 토큰의 weight는 0이 되고, 학습 시에는 teacher forcing으로 모든 위치를 동시에 계산할 수 있다.
- 08
Inference에서 가장 중요한 구조는 KV cache다. 학습 때는 전체 토큰을 한 번에 처리하지만, 추론 때는 한 토큰씩 생성한다. 매번 전체 attention을 다시 계산하면 비용이 O(n²)로 커지기 때문에 Key와 Value를 저장해 재사용한다. LLaMA-3-8B에서 32 layers, num_kv_heads 8, d_head 128, fp16 기준으로 2k context는 0.25GB, 32k는 약 4GB, 128k는 약 16GB가 된다. GQA를 무시하고 query head 32로 계산하면 운영 견적이 4배 틀린다.
- 09
KV cache를 줄이는 대표 기법에는 MQA, GQA, MLA, quantized KV cache가 있다. MQA는 모든 head가 같은 K와 V를 공유해 cache를 크게 줄이지만 품질 손실이 일부 있다. GQA는 K와 V를 group 단위로 공유해 MQA의 품질 손실과 MHA의 메모리 비용 사이를 절충하며, LLaMA-2-70B와 LLaMA-3 모두 사용한다. DeepSeek-V2와 V3의 MLA는 K와 V를 저차원 latent로 압축하고, quantized KV cache는 fp8, int8, int4로 더 압축한다.
- 10
Attention의 긴 context 비용은 계산만의 문제가 아니라 메모리 이동의 문제이기도 하다. FlashAttention은 attention 행렬 전체를 메모리에 저장하지 않고 chunk 단위로 streaming하며, log-sum-exp trick으로 chunk별 softmax를 정확히 결합한다. 그래서 FLOPs는 여전히 O(n²)이지만 활성화 메모리는 O(n)까지 줄어든다. FlashAttention-3는 H100에서 FP16 약 740 TFLOPs/s, FP8 약 1.2 PFLOPs/s를 보고했고, LLM 학습과 추론의 사실상 표준 최적화가 되었다.
- 11
Long-context를 늘리는 방법은 여러 갈래지만 깨지는 조건도 분명하다. Sliding Window는 가까운 W개 토큰만 보므로 local 작업에는 좋지만 long-range dependency가 필요한 작업에서는 정확도가 무너질 수 있다. RoPE scaling은 4배 확장에는 효과적이지만 factor 8배 이상은 fine-tune 없이 품질 폭락 위험이 있다. Speculative decoding은 output token이 100개 이상처럼 길 때 유리하고, 20 token보다 짧으면 오버헤드만 늘 수 있다. Prefix caching도 같은 prefix가 자주 재사용될 때만 prefill 비용을 줄인다.
- 12
운영자가 만나는 silent degradation은 수치 신호로 잡아야 한다. GPU memory가 95%를 넘고 batch가 들어가지 않으면 seq_len과 batch의 곱이 한도를 넘은 KV cache OOM일 수 있으며, batch를 줄이거나 seq_len cap, paged attention을 검토한다. RoPE scaling 뒤 long-context perplexity가 50% 이상 오르면 factor가 너무 큰 신호일 수 있다. Prefix cache hit ratio가 30% 아래로 떨어지면 system prompt가 자주 바뀌는지 보고, 고정 prefix와 동적 suffix를 분리한다. 정리하면 attention은 맞춤 검색과 가중 결합이고, 그 비용은 KV cache, context length, batch, decode 방식에서 운영 숫자로 드러난다.
같은 레이어