학습률 스케줄러(Learning Rate Scheduler)는 학습 도중 학습률(learning rate)을 동적으로 조정하는 기법이다. 적절한 학습률 스케줄은 수렴 속도와 최종 성능에 큰 영향을 미친다.
주요 스케줄러
python
import torch
import torch.optim as optim
import math
model = torch.nn.Linear(10, 1)
optimizer = optim.Adam(model.parameters(), lr=1e-3)
# 1. StepLR: 일정 epoch마다 감소
scheduler1 = optim.lr_scheduler.StepLR(optimizer, step_size=30, gamma=0.1)
# 2. CosineAnnealingLR: 코사인 곡선으로 감소
scheduler2 = optim.lr_scheduler.CosineAnnealingLR(optimizer, T_max=100, eta_min=1e-6)
# 3. ReduceLROnPlateau: 검증 손실이 개선 없으면 감소
scheduler3 = optim.lr_scheduler.ReduceLROnPlateau(
optimizer, mode='min', factor=0.5, patience=10, verbose=True)
# 4. OneCycleLR: 1 사이클 정책 (빠른 수렴)
scheduler4 = optim.lr_scheduler.OneCycleLR(
optimizer, max_lr=1e-2, total_steps=1000)
# 5. 워밍업 + 코사인 감소 (직접 구현)
def get_lr_with_warmup(step, warmup_steps, total_steps, max_lr):
if step < warmup_steps:
return max_lr * step / warmup_steps
progress = (step - warmup_steps) / (total_steps - warmup_steps)
return max_lr * 0.5 * (1 + math.cos(math.pi * progress))
# 커스텀 람다 스케줄러
scheduler5 = optim.lr_scheduler.LambdaLR(
optimizer,
lr_lambda=lambda step: get_lr_with_warmup(step, 100, 1000, 1.0)
)
학습 루프에서 사용
python
for epoch in range(num_epochs):
for batch in dataloader:
loss = train_step(batch)
optimizer.step()
scheduler4.step() # OneCycleLR은 배치마다
# ReduceLROnPlateau는 epoch마다 val_loss 제공
val_loss = validate()
scheduler3.step(val_loss)
# 나머지는 epoch마다
scheduler1.step()
print(f"Epoch {epoch}, LR: {optimizer.param_groups[0]['lr']:.6f}")
스케줄러 비교
| 스케줄러 | 특징 | 적합 상황 |
|---|
| StepLR | 계단식 감소 | 간단한 실험 |
| Cosine | 부드러운 감소 | 일반 딥러닝 |
| ReduceOnPlateau | 적응형 | 검증 손실 모니터링 |
| OneCycleLR | 워밍업+감소 | 빠른 수렴 필요 |
| Warmup+Cosine | 트랜스포머 표준 | LLM, ViT |
관련 개념