콘텐츠로 이동

신경망과 역전파

분류: Layer 11 - AI 기초 & 머신러닝 | 선수지식: L11-10 (ML 수학 토대), L11-30 (ML 패러다임 기초)

신경망과 역전파 — Forward, Backward, 메모리

섹션 제목: “신경망과 역전파 — Forward, Backward, 메모리”

신경망은 선형 변환과 비선형 활성화의 합성이고, 역전파는 체인룰을 적용해 손실의 gradient를 모든 가중치에 거꾸로 전파하는 알고리즘이다. 트랜스포머·LLM도 이 두 개념의 확장이다.

  • 모든 NN의 토대: 트랜스포머, CNN, RNN, LLM이 모두 이 구조의 확장
  • 학습 안정성 디버깅: NaN, vanishing/exploding gradient를 forward·backward 단계에서 추적
  • GPU 메모리 비용 모델: forward activation 저장 + AdamW state가 학습 메모리의 ~80%를 차지 — 운영자 비용 직관의 토대
  • fine-tuning 결정: full vs LoRA vs QLoRA 선택의 메모리 산식이 이 토픽 위에 깔린다

2.5 선행 기술의 한계 — 왜 다층 + 비선형 + backprop이 필요했나

섹션 제목: “2.5 선행 기술의 한계 — 왜 다층 + 비선형 + backprop이 필요했나”

선형 분류기의 한계: L11-30의 logistic regression과 단층 perceptron은 선형 비분리(non-linearly separable) 함수에서 깨진다. Minsky·Papert(1969)는 국소 연결(conjunctive localness) 제약 아래 perceptron이 parity·connectedness 같은 함수를 표현할 수 없음을 정리(Theorem 3.1.1, 5.5)로 증명했고, XOR이 직관적 사례로 굳어졌다 (Wikipedia — Perceptrons (book)). 이 결과는 1차 AI 겨울의 한 축으로 신경망 연구를 십수 년간 정체시켰다.

두 발명이 그 한계를 깼다 — 본 토픽이 다루는 골격:

  1. 다층 + 비선형 활성화 → 표현력 폭증: hidden layer 1개 + sigmoid로 임의 연속함수를 근사 가능(Cybenko 1989, UAT — Wikipedia). 단, 단일 hidden layer로 가려면 폭이 지수적으로 커져야 해서 깊이가 폭의 효율적 대안이 된다 — §3.2가 정량적으로 다룬다. 활성화 함수가 비선형성을 만들지 못하면 깊이가 아무리 늘어도 선형 변환 1개와 같다(§3.3).
  2. Backpropagation → 효율적 gradient 계산: Rumelhart·Hinton·Williams(1986, Nature 323:533)이 체인룰을 layered network에 일반화해 모든 weight의 gradient를 단일 backward pass로 얻는 절차를 정착시켰다. n개 파라미터 신경망의 finite-difference gradient는 O(n) forward pass가 필요한데 reverse-mode autodiff는 forward 비용의 23배 안에서 끝난다 — 이 비용 우위가 깊은 네트워크를 학습 가능 영역으로 끌어들였다. §3.5가 메커니즘, §3.10이 실전 디버깅을 다룬다.

이 두 발명을 곱셈으로 합성하니 새 문제(vanishing·exploding gradient) 가 생겼고, 그 한계를 §3.6 진단·§3.7 초기화·§3.8 residual·layer norm이 다시 풀어내는 연쇄가 본 토픽의 골격이다. “이 토픽이 사라지면 깨지는 것”: LLM 학습 메모리 산식(§3.9)·fine-tune 인프라 결정(§4)·신규 ML 기법 평가 5질문(§3.13)이 모두 토대를 잃는다 — backprop이 만든 동적 메모리(activation·gradient·optimizer state) 분류 위에 운영 비용 직관이 세워지기 때문이다.

y = activation(w^T x + b)
  • 활성화 함수가 없으면 logistic regression(L11-20)과 같다
  • LLM의 마지막 layer = (어휘 크기만큼 큰) softmax classifier (multinomial) — 다음 토큰 분류기. 엄밀히는 logistic이 아니라 softmax지만 같은 family
y = f3(W3 · f2(W2 · f1(W1 · x + b1) + b2) + b3)
  • 함수 합성. 각 층마다 행렬 곱 + bias + 비선형 활성화
  • Universal Approximation Theorem: 충분히 큰 hidden layer 1개로도 어떤 연속함수든 임의 정밀도로 근사 가능. 다만 “충분히 큰”이 비현실적이라 깊이가 가치를 가진다.

비선형성이 없으면 어떤 깊이라도 결국 선형 변환 1개와 같다. 활성화 함수가 표현력을 만든다.

함수특징사용처
Sigmoid1/(1+e^-x)[0,1]. vanishing gradient 위험옛 분류기, 게이트
Tanhtanh(x)[-1,1], zero-centeredRNN/LSTM
ReLUmax(0, x)단순·빠름. dying ReLU 위험CNN 표준
GELUx · Φ(x)ReLU의 부드러운 버전BERT, GPT-2/3
SiLU/Swishx · sigmoid(x)smooth, self-gatedEfficientNet, PaLM
SwiGLU(xW · SiLU(xV))gated linear unit. 표현력↑LLaMA, Mistral, Gemma
GeGLU(xW · GELU(xV))SwiGLU의 GELU 버전T5, 일부 LLM

LLM 시대 표준은 SwiGLU/GELU 계열. ReLU는 단순한 분류기에서만.

입력에서 출력까지 한 방향으로 계산:

입력 x
→ W1 x + b1 (행렬 곱)
→ activation (비선형)
→ 다음 layer ...
→ 출력 y

각 layer의 activation을 메모리에 저장한다 — backward에서 사용해야 하기 때문이다. 이게 학습 메모리의 큰 부분.

activation memory ≈ batch × seq_len × hidden_dim × num_layers × bytes

LLM 학습에서 batch size↑ 또는 seq_len↑하면 메모리가 선형으로 증가하는 출처.

손실에서 시작해 각 층의 gradient를 거꾸로 계산. 핵심은 체인룰 (L11-10 §3.4 참고).

손실 L
← dL/dy3 (출력 gradient)
← dL/dW3 = (dL/dy3) · y2^T (outer product, W3과 같은 shape)
← dL/dy2 = W3^T · (dL/dy3)
← dL/dW2 = (dL/dy2) · y1^T
← ...

forward에서 저장한 activation(y2, y1 등)을 사용해 각 가중치의 gradient를 계산한다. 그래서 forward activation 저장이 메모리에서 빠지면 backward를 못 한다 (또는 재계산해야 함 → gradient checkpointing).

깊은 신경망의 두 가지 학습 실패 모드.

종류증상원인대응
Vanishing깊은 층 가중치가 거의 안 변함sigmoid/tanh 미분이 작음, 깊이 곱셈으로 0에 수렴ReLU/GELU 활성화, residual connection, layer norm, Xavier/He init, fp16 underflow 시 loss scaling
Exploding손실 NaN, 가중치 발산큰 가중치, 깊이 곱셈으로 발산gradient clipping (L11-30 §3.8), weight init, LR↓

이 두 문제를 풀어낸 두 가지 발명이 깊은 신경망의 시대를 열었다 — ReLU 계열 활성화residual connection.

너무 작으면 vanishing, 너무 크면 exploding.

  • Xavier/Glorot: variance = 1/n_in. tanh/sigmoid 용
  • He/Kaiming: variance = 2/n_in. ReLU 용
  • Truncated normal (std=0.02): GPT-2/BERT의 initializer_range=0.02. 다만 현대 LLM(LLaMA, Mistral 등)은 깊이 보정 추가 — 출력 projection을 1/√(2L)로 스케일하여 깊이가 늘어도 안정적

가중치 초기화는 학습 첫 1000 step의 안정성을 좌우한다. 잘못된 init 하나로 학습이 발산할 수 있다.

깊은 신경망 학습 가능하게 만든 두 핵심 발명.

  • Residual (y = x + f(x)): gradient가 1 + df/dx로 전파되어 vanishing 방지. ResNet(2015) → Transformer 모두 채택.
  • Layer Norm: 한 sample 안에서 hidden 차원을 정규화. 트랜스포머 표준 (L11-20 §3.6 참고).
  • Pre-norm vs Post-norm:
    • Original Transformer = post-norm: x + LayerNorm(f(x))
    • 현대 LLM = pre-norm: x + f(LayerNorm(x)) — 학습 안정성 우위

LLM 학습에서 GPU 메모리는 다음으로 구성된다:

총 메모리 = parameters + gradients + optimizer state + activations + workspace

7B 모델 mixed-precision(fp16/bf16) 학습 기준 (ZeRO 논문 식: 16N bytes for parameters/gradients/optimizer state):

구성크기비고
Parameters (fp16)14 GB7B × 2 bytes (forward·backward 연산용)
Gradients (fp16)14 GBparameters와 같은 shape
fp32 master weights28 GB누적 업데이트 정밀도용 (mixed-precision 필수)
AdamW state — m (fp32)28 GB1차 모멘트
AdamW state — v (fp32)28 GB2차 모멘트
Activations (가변)seq_len·batchKorthikanti 식: s·b·h·L·(34 + 5·a·s/h)
합계 (activation 제외)~112 GBZeRO 식 16N bytes

운영 직관: 7B mixed-precision full fine-tune은 단일 A100 80GB로 부족(activation 포함하면 더). H100 1장 또는 ZeRO/FSDP로 multi-GPU 분산이 표준. LoRA(16-bit)는 ~24GB(RTX 4090 가능), QLoRA(4-bit base)는 68GB까지 가능 (Unsloth 활용 시).

메모리 절감 기법 (모두 trade-off 동반)

섹션 제목: “메모리 절감 기법 (모두 trade-off 동반)”
  • FlashAttention (Dao 2022): attention의 메모리 복잡도를 O(n²) → O(n) 로. 커널 fusion으로 5% 미만 오버헤드, seq_len 큰 학습에서 GB 단위 절감. seq_len 길어지면 1순위 도구
  • Gradient checkpointing: activation을 일부만 저장, backward에서 재계산. 메모리↓ 5060%, 시간↑ 2030% (selective checkpointing은 +10~15%만). NeMo·Megatron 보고
  • Mixed precision (fp16/bf16): forward·backward는 16-bit, weight 누적은 fp32 master copy. 메모리 절반·속도↑ + 정밀도 유지
  • ZeRO / FSDP (DeepSpeed/PyTorch): optimizer state·gradients·parameters를 GPU 사이 분산. Stage 1 = optimizer state만, Stage 2 = +gradients, Stage 3 = +parameters (가장 공격적)
  • LoRA(16-bit): rank r decomposition만 학습. r=8은 부족, 운영 표준 r=16~32, target_modules는 q,k,v,o,gate,up,down 7개(LLaMA류 HF PEFT 기본)
  • QLoRA: LoRA + base model을 NF4 4-bit 양자화. 7B를 6~8GB까지 끌어내림 (Unsloth 활용 시)
  • 8-bit optimizer (bitsandbytes): AdamW state를 8-bit로 양자화. ~75% optimizer state 절감
  • DoRA / rsLoRA / LoRA-FA (2024+): LoRA 변형. DoRA는 LLaMA-7B에서 +3.7% 보고
  • Liger Kernel / Unsloth (2024+): Triton fused kernel. 단일 GPU QLoRA는 Unsloth(VRAM -70%, 속도 2~3배), 멀티 GPU throughput은 Liger Kernel(메모리 -60%, throughput +20%)

PyTorch의 loss.backward()가 자동 gradient 계산. 디버깅 도구:

  • param.grad로 gradient 확인
  • torch.autograd.detect_anomaly()로 NaN 발생 위치 추적
  • 중간 activation·gradient의 norm/평균을 print해 vanishing·exploding 감지
  • torch.utils.checkpoint로 gradient checkpointing 적용

디버깅 시그널 (loud failure — 즉시 발견)

섹션 제목: “디버깅 시그널 (loud failure — 즉시 발견)”
  • gradient norm이 0에 가까움 → vanishing → 활성화·init·residual 점검
  • gradient norm이 매우 큼 (>1e3) → exploding → clipping↓ + LR↓
  • 특정 layer만 NaN → init 또는 정규화 문제
  • forward는 OK인데 backward에서 NaN → 보통 fp16 underflow → bf16 또는 loss scaling

Silent failure (에러 없이 천천히 망가짐 — 가장 위험)

섹션 제목: “Silent failure (에러 없이 천천히 망가짐 — 가장 위험)”

학습이 정상처럼 흘러가지만 결과가 틀어지는 패턴. 감지 명령과 복구를 함께 명시한다.

  • gradient checkpointing이 메모리를 거의 안 줄임 — activation이 작은 모델(<1B params)이거나 segment 수가 부적절. 감지: nvidia-smi --query-gpu=memory.used --format=csv,noheader -l 1 on/off 실행 비교 → 절감폭 5% 미만이면 효과 없음. 복구: layer 수↑·seq_len↑이거나, selective checkpointing(matmul 제외, pointwise만) — PyTorch 2.5+ create_selective_checkpoint_contexts 권장 (PyTorch blog)
  • LoRA loss는 떨어지는데 평가 점수가 base와 거의 같음 — rank 부족(r=8) 또는 target_modulesq_proj,v_proj 2개뿐. 감지: 학습 loss 곡선은 정상이지만 검증 metric 정체. 복구: r=16~32, target_modules=['q_proj','k_proj','v_proj','o_proj','gate_proj','up_proj','down_proj'] 7개 모두 (HF PEFT docs)
  • fp16 underflow의 silent 단계 — gradient가 표현 범위 아래로 떨어져 일부 layer만 가중치 업데이트가 멈춤. 감지: for n,p in model.named_parameters(): print(n, torch.isnan(p.grad).any().item(), p.grad.abs().min().item())을 step마다. 복구: bf16(H100/A100/L4) 또는 torch.cuda.amp.GradScaler
  • detect_anomaly() traceback이 무관한 layer를 가리킴 — anomaly detector는 NaN이 전파된 위치를 보여주지 발생한 위치를 보여주지 않는다 (PyTorch Forums). 50층 모델에서 layer 3에 NaN이 들어가면 한참 뒤 layer에서 에러가 발생. 복구: 각 layer에 register_forward_hook(lambda m,i,o: print(m, torch.isnan(o).any().item()))을 걸어 첫 NaN 발생 layer를 직접 찾는다

3.11 신경망의 종류 (간략 — 깊이는 후속 토픽)

섹션 제목: “3.11 신경망의 종류 (간략 — 깊이는 후속 토픽)”
  • MLP: 일반 fully connected
  • CNN: convolution + pooling. 이미지·시퀀스 일부에 강함
  • RNN/LSTM/GRU: 순차 처리. 트랜스포머에 대부분 밀림
  • Transformer: attention 기반. LLM·번역·이미지(ViT) 표준 → L11-50

3.12 깨지는 조건 정량 표 (운영 결정용)

섹션 제목: “3.12 깨지는 조건 정량 표 (운영 결정용)”
기법효과 발휘 범위깨지는 조건
LoRA r=8작은 task·명확한 형식도메인 데이터 50K+ → r=16~32로 ↑
LoRA r=16~32일반 도메인 fine-tune코드·수학·복잡 reasoning → r=64~128 또는 full FT
LoRA target=q,k,v,obase 모델 형식 학습새 도메인 어휘·구조 → +gate,up,down 7개 모두
Gradient checkpointlayer 수↑·seq_len↑작은 모델(<1B)에선 거의 효과 없음
FlashAttention대부분의 H100·A100sm_60 이하 GPU(T4, P100)는 미지원 → SDPA fallback
bf16H100·A100·TPUsm_75 이하 GPU(T4)는 fp16 + loss scaling 필요
Pre-norm깊은 트랜스포머(>20층)얕은 모델은 post-norm이 약간 우위 (legacy 가치)
ZeRO-3 (FSDP)70B+ 모델, multi-GPU<10B + 단일 GPU에선 통신 오버헤드만 증가

이 표는 운영자가 fine-tune·학습 인프라 결정 시 첫 참고. 측정 후 재조정.

3.13 신경망 메모리 산식의 일반 매핑 (Transferable Pattern)

섹션 제목: “3.13 신경망 메모리 산식의 일반 매핑 (Transferable Pattern)”

NN 메모리 = 정적(parameter) + 동적(activation·gradient·optimizer state)는 다른 시스템 비용 모델과 같은 패턴.

NN 메모리일반 시스템 비용 매핑
Parameters (정적)데이터베이스 schema·인덱스 storage
Activations (forward)캐시·sliding window 메모리
Gradients (backward)event log·undo buffer
Optimizer state (m, v)metadata·index for adaptive system
Mixed precision (fp16)int8 column storage·압축 표 (DB)
Gradient checkpointingrecomputation vs storage trade-off (CDN, view cache)

일반 공식: “정확도 vs 메모리 vs 시간”의 3축 trade-off — 어떤 시스템 설계에도 적용된다. NN backprop이 특별한 게 아니라 일반 컴퓨팅 비용 모델의 한 사례.

새 ML 기법을 만났을 때 던지는 질문 5가지

섹션 제목: “새 ML 기법을 만났을 때 던지는 질문 5가지”

PagedAttention·RoPE·MoE·MLA 같은 처음 보는 기법을 평가할 때 이 질문들로 분해하면 trade-off 위치가 드러난다. 매핑 표(위)와 §3.12 깨지는 조건 표를 함께 사용한다.

  1. 정적 vs 동적 메모리 중 어디를 건드리는가 — parameter 압축(정적, 예: QLoRA NF4) vs activation·KV cache 절감(동적, 예: FlashAttention/PagedAttention). 후자는 batch·seq_len에 비례하므로 운영 부하 곡선과 직결.
  2. 3축(정확도·메모리·시간) 중 어느 둘을 trade하는가 — checkpointing(메모리↔시간), LoRA(정확도 약간↔메모리·시간), FlashAttention(거의 무손실 — 상수항 IO만 줄임).
  3. 어떤 깨지는 조건에서 효과가 사라지는가 — 작은 모델, 짧은 seq, 특정 GPU 아키텍처(sm_75 이하 미지원 등). §3.12 표가 1차 답이며, 새 기법은 같은 형식으로 한 줄을 추가한다.
  4. silent failure가 가능한가 — 에러 없이 효과만 사라지는 경우. 감지 신호(metric·임계값)와 측정 명령을 §3.10 형식으로 미리 정의.
  5. 다른 도메인의 등가물은 무엇인가 — gradient checkpointing은 CDN re-fetch, mixed precision은 DB int8 column. 패턴이 같으면 운영 직관이 이전된다.

§4 운영 시나리오의 “QLoRA + Unsloth 선택”은 이 5질문을 거친 결과다 — 질문 1·2로 정적(NF4 quant)+동적(activation) 양쪽 절감을 확인, 질문 3으로 “도메인 데이터 50K+이면 r=8로 부족” 깨지는 조건 점검, 질문 4로 “loss는 떨어지지만 평가 정체” silent failure 감지 명령 마련. 질문이 빠지면 결정 근거가 추정으로 무너진다.

  • LLM fine-tuning (full / LoRA / QLoRA)
  • 임베딩 모델 학습 (contrastive)
  • 분류기 (LLM 라우팅, intent classification)
  • 추천 시스템 (deep neural recommender)
  • 이상 탐지 (autoencoder)

운영 시나리오 — 7B 모델 fine-tune 인프라 결정 (예시)

섹션 제목: “운영 시나리오 — 7B 모델 fine-tune 인프라 결정 (예시)”
상황: 한국어 도메인 데이터 5K, base = LLaMA-3-8B
선택지:
A. Full FT (단일 H100 80GB):
- 메모리 ~112GB → 단일 GPU 부족 → ZeRO-3 multi-GPU 필요
- 비용: H100 4× × 24h = ~$200
B. LoRA r=16 (RTX 4090 24GB):
- 메모리 ~24GB OK
- 비용: 4090 × 24h = ~$30
- 품질: full FT 대비 95~100%
C. QLoRA + Unsloth (4090 단독):
- 메모리 ~6~8GB OK, 속도 2~3×
- 비용: ~$15
- 품질: full FT 대비 90~95%
선택: C (QLoRA + Unsloth). 도메인 데이터 5K로 LoRA 충분.
대안 비선택: A는 비용 자릿수 차이. B는 LR 4090 단독 가능하나 Unsloth가 더 빠름.
결과 (가상): 학습 4h, 평가 점수 +15%p, 비용 $15.

§3.9 메모리 산식 + §3.12 깨지는 조건 표 + §3.13 일반 매핑이 모두 이 결정에 적용된다.

결정 분기 (데이터 규모에 따라 갈래가 바뀜):

  • 5K ~ 50K, 일반 도메인 (현 시나리오): C가 표준. r=16~32, target_modules는 attention 4개부터 시작.
  • 50K ~ 500K, 일반 도메인: B로 갈아탐 (LoRA 16-bit r=32, target_modules 7개 모두). QLoRA의 4-bit 양자화 손실이 데이터 규모에서 누적되기 시작 — 정확도 차이가 비용 차이를 정당화하는 구간.
  • 500K+ 또는 코드·수학·복잡 reasoning: A (Full FT 또는 ZeRO-3/FSDP) 검토. §3.12 표의 “LoRA r=64~128 또는 full FT” 행이 발동.
  • <1B 모델: gradient checkpointing 효과 거의 없음(§3.10 silent failure 1번) — A에서도 layer 수·seq_len이 작으면 메모리 절감폭 < 5%.

실패 시 라우팅: C 진행 후 학습 loss 곡선은 정상인데 평가 metric이 base와 거의 같으면 §3.10의 “LoRA loss는 떨어지는데 평가 정체” silent failure로 진단을 시작한다. 1차 조치: rank 증가(8 → 16/32)와 target_modules 7개 확장. 2차 조치: 도메인 데이터의 형식·다양성 점검(5K가 실제로는 1K의 5배 복사면 분기 첫 줄부터 깨짐). 3차에서도 정체면 데이터 수집 또는 base 모델 교체로 escalate — 알고리즘 튜닝 단계를 벗어났다는 신호.

플랫폼 엔지니어가 LLM 운영할 때 신경망·메모리 직관이 다음에 도움 된다.

  • GPU 인스턴스 결정: 7B fp16 full fine-tune = A100 80GB. 7B LoRA = RTX 4090. §3.9 표가 직접 적용
  • Mixed precision 선택: fp16(loss scaling 필요, overflow 위험) vs bf16(H100 표준, 안전) — H100/A100/L4 GPU에 따라 다름
  • fine-tune 비용 견적: 학습 시간 = (data tokens / throughput) × hourly cost. throughput은 batch×seq_len에 비례
  • 장애 대응: fine-tuning 로그에서 NaN, gradient norm 폭증 같은 시그널을 식별해 적절히 escalate
  • 2026 운영 디폴트 도구: 단일 GPU 7B QLoRA는 Unsloth(VRAM -70%, 속도 2~3배), 멀티 GPU throughput은 Liger Kernel. fine-tuning 비용 견적식에 직접 영향
개념 A개념 B차이점
ForwardBackwardactivation 계산 vs gradient 계산
SigmoidSoftmax단일 [0,1] 출력 vs 합 1 분포
ReLUGELUpiecewise linear vs smooth (트랜스포머 선호)
Xavier initHe inittanh/sigmoid 용 vs ReLU 용
Pre-normPost-normnorm 위치, pre-norm이 학습 안정성 우위
fp16bf16정밀도 우위 vs 표현 범위 우위 (overflow에 robust)
Activation memoryOptimizer memoryforward 저장 buffer vs AdamW의 m,v buffer
Gradient checkpointingFull activation시간↑·메모리↓ vs 시간↓·메모리↑
Full fine-tuneLoRA모든 가중치 vs 일부 rank-r adapter
  • 신경망 한 층의 forward와 backward를 행렬 곱으로 설명할 수 있다
  • vanishing vs exploding gradient의 원인과 표준 대응 3가지를 구분할 수 있다
  • LLM 7B 학습이 GPU 80GB+ 필요한 이유를 §3.9 표로 분해할 수 있다
  • Residual connection이 깊은 신경망 학습을 가능하게 한 이유를 gradient 관점에서 설명할 수 있다
  • Pre-norm이 트랜스포머 표준이 된 이유를 학습 안정성 관점에서 말할 수 있다
  • Gradient checkpointing의 시간↔메모리 trade-off와 적용 시점을 설명할 수 있다
  • LoRA가 메모리·계산을 줄이는 메커니즘(r 차원 분해)을 설명할 수 있다
  • 활성화: ReLU, Leaky ReLU, ELU, GELU, SiLU/Swish, SwiGLU, GeGLU, Mish
  • 초기화: Xavier/Glorot, He/Kaiming, truncated normal, μP (muP)
  • 정규화: BatchNorm, LayerNorm, RMSNorm, GroupNorm, T-Fixup
  • 메모리 최적화: gradient checkpointing, ZeRO-1/2/3, FSDP, DeepSpeed, FlashAttention
  • PEFT: LoRA, QLoRA, DoRA, LoRA-FA, prefix tuning, IA³
  • Autograd: reverse-mode autodiff, JAX vjp, PyTorch torch.autograd.grad

손계산 결과를 PyTorch와 매치시키는 풀 스크립트. 2-2-1 MLP, ReLU, MSE.

import torch
x = torch.tensor([[1.0, 2.0]])
y_true = torch.tensor([[1.0]])
W1 = torch.tensor([[0.1, 0.2], [0.3, 0.4]], requires_grad=True)
b1 = torch.zeros(2, requires_grad=True)
W2 = torch.tensor([[0.5], [0.6]], requires_grad=True)
b2 = torch.zeros(1, requires_grad=True)
h = torch.relu(x @ W1 + b1)
y = h @ W2 + b2
loss = ((y - y_true) ** 2).mean()
loss.backward()
print(f"y={y.item():.4f}, loss={loss.item():.4f}")
print("dL/dW2=", W2.grad.flatten().tolist())
print("dL/dW1=", W1.grad.flatten().tolist())

예상 출력:

y=0.9500, loss=0.0025
dL/dW2= [-0.07, -0.10]
dL/dW1= [-0.05, -0.06, -0.10, -0.12]

손계산 매치: pre-activation x @ W1 = [0.7, 1.0] → ReLU 통과 → y = 0.7·0.5 + 1.0·0.6 = 0.95. dL/dy = 2(y - y_true)/N = -0.10 (N=1이므로 평균/합 동일), dL/dW2 = h^T · dL/dy = [0.7, 1.0]^T · -0.10. 결과가 다르면 (1) ReLU 음수 입력의 derivative 0 처리 누락, (2) MSE에서 sum()을 썼다면 N으로 나누지 않아 gradient가 mean() 대비 N배 커진다 (batch>1에서 결정적).

다음 단계: 활성화를 sigmoid로 바꾸어 dL/dhsigmoid(z)·(1-sigmoid(z))가 곱해져 vanishing의 씨앗이 어디서 생기는지 확인.

메모리 직관 — gradient checkpointing 측정

섹션 제목: “메모리 직관 — gradient checkpointing 측정”

torch.utils.checkpoint의 메모리·시간 trade-off를 직접 측정. CUDA 필요.

import time, torch
import torch.nn as nn
from torch.utils.checkpoint import checkpoint_sequential
device = "cuda"
model = nn.Sequential(*[nn.Linear(4096, 4096) for _ in range(32)]).to(device)
x = torch.randn(8, 4096, device=device, requires_grad=True)
def run(use_ckpt):
torch.cuda.reset_peak_memory_stats()
t0 = time.time()
out = checkpoint_sequential(model, segments=4, input=x, use_reentrant=False) if use_ckpt else model(x)
out.sum().backward()
torch.cuda.synchronize()
return torch.cuda.max_memory_allocated() / 1e9, time.time() - t0
mem_off, t_off = run(False)
mem_on, t_on = run(True)
print(f"off: mem={mem_off:.2f} GB, time={t_off:.3f} s")
print(f"on : mem={mem_on:.2f} GB, time={t_on:.3f} s")
print(f"saved {(1-mem_on/mem_off)*100:.0f}% mem, +{(t_on/t_off-1)*100:.0f}% time")

예상 출력 (A100 40GB, 32×Linear(4096→4096), 위 스크립트):

off: mem=2.30 GB, time=0.045 s
on : mem=0.95 GB, time=0.063 s
saved 59% mem, +40% time

문헌 수치 — 보고된 trade-off 분포는 “메모리 −5080%, 시간 +1030%” 범위 (PyTorch Forums benchmark). 측정 결과가 5% 미만 절감이면 §3.10의 silent failure 후보 — segments 수를 늘리거나 모델 깊이·hidden_dim을 키워 다시 측정.

남은 측정 항목 (체크리스트):

  • HuggingFace transformers로 1B/7B 모델을 fp32 / fp16 / bf16로 각각 load해 torch.cuda.memory_allocated() 비교 → 자릿수 차이 확인
  • HuggingFace PEFT로 1B 모델에 LoRA(r=8) → r=16 → r=32로 변경하며 메모리·시간·평가 점수 곡선 그리기. 평가 점수가 r 증가에 무감응이면 silent failure 가능성
  • 의도적으로 큰 weight init(std=10.0)으로 exploding gradient 발생시키고 torch.autograd.detect_anomaly()로 NaN 발생 위치 추적
  • 10층 sigmoid MLP를 학습시켜 깊은 층 gradient가 거의 0인지 확인 → ReLU로 바꾸어 vanishing 완화 확인
  • mixed precision 켰는데 NaN → fp16 overflow. bf16 시도 또는 torch.cuda.amp.GradScaler로 loss scaling
  • gradient checkpointing이 메모리 거의 안 줄임 → activation이 작은 모델임. layer 수↑ 또는 seq_len↑ 모델에서 효과 큼
  • LoRA가 full fine-tune보다 성능 폭락 → rank 부족(r=8 → 16/32) 또는 target module 부적절(q_projk_proj/v_proj/o_proj도 추가)
  1. 신경망은 선형 변환과 비선형 활성화의 합성, 역전파는 체인룰로 gradient를 거꾸로 전파하는 알고리즘이다.
  2. Vanishing/exploding gradient는 깊이 곱셈에서 발생하며, ReLU 계열·residual·layer norm·gradient clipping이 표준 대응이다.
  3. LLM 학습 메모리는 parameters + gradients + AdamW state(파라미터의 ~4배) + activations로 구성되어 7B 모델도 80GB+ 필요하다.
  4. Gradient checkpointing·mixed precision·ZeRO/FSDP·LoRA가 메모리를 줄이는 표준 기법이고 모두 trade-off가 있다.
  5. 트랜스포머의 attention·layer norm·residual은 모두 이 기본 신경망 구조의 확장이고, LLM 운영자 비용 직관의 토대다.

최종 수정: 2026-04-25