Gradient Descent is how models learn. We start at random weights and take small steps in the direction of steepest descent — opposite the gradient — to reach minimum loss.
| Variant | Samples/step | Pros | Cons |
|---|---|---|---|
| Batch GD | All n | Stable, exact gradient | Slow per step |
| Stochastic GD | 1 | Fast, noisy escapes minima | High variance |
| Mini-batch GD | 32–256 | Best of both worlds | Batch size is a hyperparameter |
- Start with Adam optimizer (lr=1e-3) — it handles most cases well out of the box
- If training loss plateaus, try reducing lr by 10x or use a cosine annealing schedule
- If training loss oscillates wildly → lr is too high — halve it until stable
- Use gradient clipping (
max_norm=1.0) for RNNs and transformers to prevent exploding gradients - Monitor both train loss and val loss — divergence means you're overfitting (see Learning Curves)
- Adam usually converges faster and with less tuning than plain SGD; well-tuned SGD with momentum often generalises as well or better on vision tasks (Wilson et al. 2017)
- GPT-3 was trained with Adam (β₁ = 0.9, β₂ = 0.95), a linear warmup over the first 375M tokens, then cosine decay (Brown et al. 2020)
- Very large batches can generalise worse unless the learning rate and warmup are scaled with them (Keskar et al. 2017; Goyal et al. 2017)
- Mixed-precision training (FP16/BF16) roughly halves activation memory and speeds training considerably on GPUs with tensor cores, usually without loss of accuracy (Micikevicius et al. 2018)
pip install torch scikit-learn
import torch
optimizer = torch.optim.AdamW(model.parameters(), lr=1e-3, weight_decay=1e-2)
for epoch in range(20):
model.train()
optimizer.zero_grad()
pred = model(X_train)
loss = loss_fn(pred, y_train)
loss.backward()
torch.nn.utils.clip_grad_norm_(model.parameters(), max_norm=1.0)
optimizer.step()
Minimising (w − 3)² from w = 0. With a learning rate of 0.1, ten steps reach 2.68, closing in on 3. With 1.1 each step overshoots further than the last and ten steps end at −15.6. For this curve any rate above 1 diverges: the step size is not a detail, it decides whether learning happens at all.
- Real loss surfaces are not one bowl; gradient descent finds a nearby low point, not the lowest.
- A good learning rate depends on the curvature, which differs between directions (see Optimizers).
- Stochastic gradients from mini-batches are noisy; the loss does not fall every step.
def descend(lr, steps=10, w=0.0):
for _ in range(steps):
w -= lr * 2 * (w - 3) # gradient of (w - 3)^2
return w
good = descend(0.1) # converging towards 3
too_big = descend(1.1) # each step overshoots furtherAssumes import numpy as np. Each snippet carries its own example numbers; the comments say which are made up or simulated.
- Deep Learning, I. Goodfellow, Y. Bengio & A. Courville, MIT Press, 2016 — chapter 4
- Convex Optimization, S. Boyd & L. Vandenberghe, Cambridge University Press, 2004 — chapter 9
Last reviewed October 2026 · How this site checks its content · Report a mistake
1. The loss jumps around and grows during training. What is the most likely cause?
Show answer
C. Too large a step crosses the valley and lands higher on the other side; repeated, the loss diverges.
2. In which direction does the gradient of the loss point?
Show answer
A. The negative gradient is the locally steepest way down — not necessarily the shortest way to the minimum.
3. Why scale features before gradient descent?
Show answer
C. With similar scales the contours are rounder, and one learning rate suits every direction.
- LLM EngineeringBatching & ThroughputServing hundreds of concurrent requests efficiently
- Chart PatternsRising WedgeBoth lines slope up but converge — momentum is dying
- Technical IndicatorsRate of ChangeSpeed rather than level: the percentage change over N bars, the first derivative of price
- The ToolkitOptunaSmart hyperparameter tuning — TPE, pruning, study visualisation, any framework
- Timeseries EngineeringDifferencingThe simplest way to make a series stationary
- Timeseries EngineeringRNNs for Time SeriesSequence processing with recurrent memory