Code N Curry MLCode & Curry ML
Back to Library
CURRICULUM: S4 · E11 · 16 min
VERIFIED BLUEPRINT

Overfitting vs Underfitting: Season to Taste

TIME: 16 min
🍽️YIELD: 1 bias-variance compass for every model you will ever tune
📓CHAPTER: S4E11

The Idea

CONCEPT
Three plates: degree-1 line missing the curve ('under-seasoned'), degree-3 hugging it ('just right'), degree-9 wiggling through every noisy dot ('memorised the noise'). Below, the U-curve: train error always falling, test error dipping then climbing. Margin: 'the gap IS the overfit.'

Training error is a rigged exam — the model graded itself on questions it studied. Only held-out error measures learning.

Underfit = too little capacity (high bias): wrong on everything, including training data. Overfit = too much (high variance): perfect on training, lost on test.

The cures for overfitting are boring and reliable: more data, regularisation (Ridge/Lasso), early stopping, simpler models, dropout.

Learning curves diagnose which disease you have: both errors high and close → bias; train low and test high → variance.

In the Test Kitchen: crank the degree to 9, then hit NEW PLATES — the wild wiggles change completely. A model that changes that much was never describing the dish.

⚗️ The Test Kitchen

INTERACTIVE LAB

Don't just read the recipe — taste it. Drag, click and break things below.

EXP 01

Season to Taste

"trust the plates you never tasted"

Filled dots are training plates the chef tastes; hollow ones are test plates held back. Raise the polynomial degree: training error always falls, but past the sweet spot the test error turns and climbs — the recipe fits the noise, not the dish. That gap is overfitting.

chilli amount →taste score ↑dashed = true recipe
TRAIN MSE
0.0129
TEST MSE
0.0189

verdict: under-seasoned (high bias)

FIG L.8: BIAS–VARIANCE — TRAIN ERROR ONLY EVER FALLS; TEST ERROR IS U-SHAPED. TRUST THE HOLLOW PLATES

The Recipe

CODE
REQUIRED SPICESoverfittingbias-variancetrain/test gapregularisationmodel capacity
Watching the U-curve appear
from sklearn.preprocessing import PolynomialFeatures
from sklearn.linear_model import LinearRegression
from sklearn.pipeline import make_pipeline
from sklearn.metrics import mean_squared_error as mse

for degree in (1, 3, 9):
    model = make_pipeline(PolynomialFeatures(degree), LinearRegression())
    model.fit(X_train, y_train)
    print(degree,
          mse(y_train, model.predict(X_train)),   # always shrinks
          mse(y_test,  model.predict(X_test)))    # U-shaped — trust this one
NEXT EXPERIMENT
CODE & CURRY
APPROVED
ML KITCHEN