Skip to content

fix(cosine): remove erroneous restart, match PyTorch CosineAnnealingLR behavior#5191

Open
DeathSurfing wants to merge 3 commits into
tracel-ai:mainfrom
DeathSurfing:fix/cosine-annealing-no-restart
Open

fix(cosine): remove erroneous restart, match PyTorch CosineAnnealingLR behavior#5191
DeathSurfing wants to merge 3 commits into
tracel-ai:mainfrom
DeathSurfing:fix/cosine-annealing-no-restart

Conversation

@DeathSurfing

Copy link
Copy Markdown

Summary

Fixes #5128

The CosineAnnealingLrScheduler was wrapping its iteration counter with % (self.num_iters + 1), causing the learning rate to abruptly jump back to max_lr after every num_iters + 1 steps. This created an erroneous half-cosine restarting waveform instead of the standard cosine annealing schedule.

Changes

  • Line 92: Removed the % (self.num_iters + 1) wrapping from step(). The current_iter now increases monotonically (via wrapping_add(1)), matching PyTorch's CosineAnnealingLR which explicitly states "performs cosine annealing without restarts, so T_cur = t and increases monotonically with each call to step()"
  • Doc updates: Config and struct docs now describe the scheduler as performing cosine annealing without warm restarts, with the iteration counter increasing monotonically
  • Test update: test_lr_change now verifies a full 5-step smooth cosine curve rather than the previous 4-step sequence that expected an artificial restart

Verification

  • All 7 cosine tests pass (cargo test -p burn-optim -- lr_scheduler::cosine)
  • All 95 burn-optim tests pass (cargo test -p burn-optim)
  • The fix is a one-line code change (removing % (self.num_iters + 1)); the rest is documentation and test updates

Reference

PyTorch CosineAnnealingLR docs

Remove the modulo operation that wraps current_iter back to 0 after
num_iters steps, causing the learning rate to abruptly jump back to
max_lr. Now current_iter increases monotonically, matching PyTorch's
CosineAnnealingLR behavior which explicitly states 'without restarts,
T_cur = t and increases monotonically with each call to step()'.

Update test_lr_change to verify the smooth full-period cosine curve
without artificial restarts.
Update the CosineAnnealingLrSchedulerConfig doc to reflect that this
scheduler performs cosine annealing without restarts (matching PyTorch's
CosineAnnealingLR). Clarify that the LR continues along the cosine curve
past num_iters without resetting, and update the num_iters field doc to
describe it as the number of iterations to reach min_lr.
Update CosineAnnealingLrScheduler doc to clarify that while the formula
originates from the SGDR paper, the implementation performs cosine
annealing without periodic restarts. The iteration counter increases
monotonically, continuing along the cosine curve past num_iters.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

CosineAnnealingLrScheduler displays non-standard behavior

1 participant