Classical Machine Learning, lesson 2
Linear regression
Fit a line by mean squared error, with gradient steps or one formula.
Fitting needs a score for how wrong a line is. This lesson builds that score, then finds the line that makes it smallest in two ways: by small steps downhill, and by one formula. You need the five flats from "Learning a function from examples": features, a label and a model with numbers to fill in.
By the end, you can:
Part 1. Mean squared error scores a line
Score a line by its mean squared error.
Keep one feature of the five flats, the area: 40 m² for $1,350, 50 for $1,400, 60 for $1,700, 80 for $2,200 and 100 for $2,450. A line through them is rent = w × area + b, with a slope w in dollars per m² and an intercept b. Try w = 25 and b = 200.
Example 1.1
Scoring rent = 25 × area + 200
How far is the line rent = 25 × area + 200 from the five flats, in one number?
- Predict each flat1,200, 1,450, 1,700, 2,200, 2,700
25 × 40 + 200 = 1,200, and so on.
- Take actual minus predicted150, −50, 0, 0, −250
Positive means the line runs below that flat.
- Square each gap22,500 + 2,500 + 0 + 0 + 62,500 = 87,500
The signs disappear, and the big miss now makes up most of the total.
- Average87,500 ÷ 5 = 17,500
One number for the whole line. Lower is better.
Answer17,500, a typical miss of √17,500 ≈ $132.
Why square? The gaps add up to −150, so their plain average is −30, which looks nearly perfect because misses in opposite directions cancel. Squaring stops that, makes one big miss cost more than several small ones, and gives a smooth score with an exact formula for its lowest point.
Residual and mean squared error
A residual is actual minus predicted, for one row. The mean squared error, MSE, is the average of the squared residuals. Its square root is back in the label's units: a typical miss.
MSE = (r₁² + r₂² + … + rₙ²) ÷ n
The line rent = 20 × area + 500 leaves residuals of 50, −100, 0, 100 and −50: an MSE of 5,000, a typical miss of about $71. No line does better on these flats, as part 3 shows. If big misses cost you no extra, average the sizes of the misses instead: the mean absolute error.
Your turn
Line P misses one flat by $300 and gets the other four exactly right. Line Q misses all five flats by $60 each. Which has the higher mean squared error?
Part 2. Gradient descent walks downhill
Take a gradient-descent step, and pick a learning rate that neither stalls nor explodes.
Every pair (w, b) has its own MSE, and for squared error they form a bowl with the best line at the bottom. The gradient says which way is downhill: how fast the MSE changes as you nudge each number. For b it's −2 × the average residual. For w it's −2 × the average of area × residual.
Example 2.1
One step from w = 25, b = 200
The line rent = 25 × area + 200 leaves residuals of 150, −50, 0, 0 and −250. Take one step, with a learning rate of 0.0001.
- Gradient for b−2 × (−150 ÷ 5) = 60
The residuals add up to −150: overall the line is too high, so b should come down.
- Gradient for w−2 × (−21,500 ÷ 5) = 8,600
Area × residual is 6,000, −2,500, 0, 0 and −25,000. The 100 m² flat dominates.
- Step against bothw: 25 − 0.0001 × 8,600 = 24.14, b: 200 − 0.0001 × 60 = 199.994
Each number takes a step the opposite way to its gradient, sized by the learning rate.
- Score the new line17,500 → 13,669
Then repeat from the new line.
Answerw = 24.14 and b = 199.994, and the MSE falls from 17,500 to 13,669.
Gradient descent and learning rate
Gradient descent fits a model by repeated small steps: work out the gradient of the loss for every parameter, move each one a little against it, and repeat until the loss stops falling. The learning rate scales each step.
new w = w − learning rate × gradient for w
Look at the two moves: w by 0.86, b by 0.006. w's gradient multiplies every residual by an area of 40 to 100, so it's far bigger. At this rate b crawls: about 177,000 steps to get within $10 of 500. Ten times the rate, and w overshoots further each step until the MSE explodes.
The fix is to rescale the area: subtract its average, 66, and divide by its spread, about 21.5. Both gradients then come out the same size, and a rate of 0.2 suits both. "Preparing features" covers rescaling.
Your turn
Start instead from w = 15 and b = 500. The residuals are 250, 150, 300, 500 and 450, and area × residual adds up to 120,500. With a learning rate of 0.0001, where does w go?
Part 3. One formula finds the best line
Find the least-squares line directly, with no steps.
For squared error, the bottom of the bowl can be found exactly. Measure each flat's gap from the average flat: dx for area and dy for rent. The slope is the sum of dx × dy over the sum of dx × dx. The intercept then puts the line through the average flat.
Example 3.1
The best line for the five flats
Find the slope and intercept that give the five flats the lowest possible MSE.
- Average each columnarea 66, rent 1,820
The areas add up to 330 and the rents to 9,100: 330 ÷ 5 = 66 and 9,100 ÷ 5 = 1,820.
- Measure the gapsdx: −26, −16, −6, 14, 34, dy: −470, −420, −120, 380, 630
Small flats sit below both averages, big flats above.
- Add up dx × dyΣ(dx × dy) = 46,400
The products are 12,220, 6,720, 720, 5,320 and 21,420, all positive: each flat sits on the same side of both averages.
- Add up dx²Σ(dx²) = 2,320
676, 256, 36, 196 and 1,156 added up: how spread out the areas are.
- Divide, then place the line46,400 ÷ 2,320 = 20, 1,820 − 20 × 66 = 500
The intercept makes the line pass through the average flat.
Answerrent = 20 × area + 500, the line gradient descent was heading for.
Each flat suggests a slope of its own, dy ÷ dx: for the 100 m² flat, 630 ÷ 34 ≈ 18.5. The formula averages these suggestions and gives flats far from the average area more say, since noise moves their slopes less.
Least squares and closed form
Least squares picks the parameters with the smallest sum of squared residuals, which is also the smallest MSE. For a line the answer has a closed form: a formula you compute directly, with no steps.
slope = Σ(dx × dy) ÷ Σ(dx²), intercept = average rent − slope × average area
With several features, the best weights solve the normal equations, (XᵀX) w = Xᵀy, where X has one row per flat plus a column of 1s. That gets slow with tens of thousands of features, and most losses have no formula, so most models, neural networks included, are fitted by steps.
Your turn
Fit a line to four points: (0, 1), (1, 3), (2, 2) and (3, 6). What are the least-squares slope and intercept?
Part 4. Reading the fitted line
Read a coefficient and R², without reading too much into them.
In rent = 20 × area + 500, the 20 says each extra m² goes with $20 more a month. Its units are the label's over the feature's: per square foot (1 m² ≈ 10.76 sq ft) it's $1.86, with identical predictions. To judge the whole fit, compare it with always guessing the average rent.
Example 4.1
How much of the spread the line explains
How much better is rent = 20 × area + 500 than predicting the average rent, $1,820, for every flat?
- Spread before the model470² + 420² + 120² + 380² + 630² = 953,000
The squared gaps of the rents from their average: what always guessing $1,820 leaves.
- Spread after the model50² + 100² + 0² + 100² + 50² = 25,000
The squared residuals of the fitted line.
- Take the share explained1 − 25,000 ÷ 953,000 ≈ 0.974
The line removes 97.4% of the squared spread.
AnswerR² ≈ 0.974.
Coefficient and R²
A coefficient is the weight on one feature: how much the prediction changes when that feature rises by 1 and the others stay the same. R² is the share of the label's spread around its average that the model explains: 1 is perfect, 0 is no better than the average.
R² = 1 − (sum of squared residuals ÷ sum of squared gaps from the average)
A coefficient describes a pattern, not a cause. Buildings with a concierge sit on dear streets, so a rent model may put a big weight on "concierge", but hiring one wouldn't add that much to the rent. The same goes for any feature you could change.
R² on the rows a model was fitted on creeps towards 1 as you add features, even random ones, so measure it on new rows. There it can even drop below 0, when the model does worse than guessing the new rows' own average.
Your turn
On five new flats, a model's squared residuals add up to 60,000. The squared gaps of those rents from their own average add up to 50,000. What is the model's R² on them?
Where you'll meet it
A common screen: derive the gradient of the MSE for a line, then say when you'd use gradient descent rather than the formula. The formula is exact but slows down with very many features. Steps scale to big data and work for losses with no formula.
scikit-learn's LinearRegression is plain least squares, solved by SciPy's lstsq, which works on X itself rather than XᵀX and so stays accurate when two columns are near copies. For more than about 10,000 training rows, scikit-learn's guide suggests SGDRegressor, which fits by gradient steps.
import numpy as np
from sklearn.linear_model import LinearRegression
area = np.array([40, 50, 60, 80, 100], dtype=float)
rent = np.array([1350, 1400, 1700, 2200, 2450], dtype=float)
# 1. The formula: slope from the gaps to the averages, then the intercept
dx, dy = area - area.mean(), rent - rent.mean()
slope = (dx * dy).sum() / (dx * dx).sum()
print(f"formula: slope {slope:.2f}, intercept {rent.mean() - slope * area.mean():.2f}")
# 2. scikit-learn's least-squares solver
model = LinearRegression().fit(area.reshape(-1, 1), rent)
print(f"sklearn: slope {model.coef_[0]:.2f}, intercept {model.intercept_:.2f}")
# 3. Gradient descent on rescaled area, 20 steps at learning rate 0.2
z = dx / area.std() # area minus 66, divided by about 21.5
a, c = 0.0, 0.0 # rent = a × z + c
for step in range(20):
err = rent - (a * z + c)
a += 0.2 * 2 * (err * z).mean() # step against the gradient
c += 0.2 * 2 * err.mean()
w = a / area.std() # back to dollars per m²
print(f"descent: slope {w:.2f}, intercept {c - w * area.mean():.2f}")
mse = ((rent - model.predict(area.reshape(-1, 1))) ** 2).mean()
print(f"MSE {mse:.0f}, R² {1 - mse / rent.var():.3f}")
# formula: slope 20.00, intercept 500.00
# sklearn: slope 20.00, intercept 500.00
# descent: slope 20.00, intercept 499.98
# MSE 5000, R² 0.974The formula and scikit-learn agree to the cent. Twenty gradient steps on rescaled area, starting from 0, stop 2 cents short of $500. The last line prints the MSE from part 1 and the R² from part 4.
Check yourself
Three questions from across the lesson. Try each one before you look back.
1
You fit rent = w × area + b by gradient descent with area in m², and at a learning rate of 0.0001 the intercept b barely moves. To hurry it along, you raise the rate tenfold, to 0.001. What happens?
2
A rent model fitted on area and bedrooms gives 22 dollars per m² and −60 dollars per bedroom. What does the −60 tell you?
3
A least-squares line fitted to the five flats always passes through one particular point. Which?
What to remember
1Mean squared error scores a line
MSE is the average squared residual: 17,500 for the line 25 × area + 200, and 5,000 for the best line, a typical miss of $71.
2Gradient descent walks downhill
Gradient descent steps each number the opposite way to its gradient, sized by the learning rate: in raw m², any rate above about 0.0002 explodes, so rescale features first.
3One formula finds the best line
Least squares has a closed form: the slope is Σ(dx × dy) ÷ Σ(dx²), here 46,400 ÷ 2,320 = 20, and the line passes through the average point.
4Reading the fitted line
A coefficient is a pattern with the other features held fixed, not a cause, and R² = 1 − 25,000 ÷ 953,000 ≈ 0.974 is the share of spread explained.
Recap and going further
The lesson on one page
- Actual minus predicted, one per row
- Positive: the line runs below that row
- Square each residual, then average
- One big miss costs more than several small ones
- Move each number a little against its gradient, repeat
- Too big a learning rate and it blows up
- Raw m² make the slope's gradient huge and the intercept crawl
- Rescale the feature and both move together
- slope = Σ(dx × dy) ÷ Σ(dx²)
- The line passes through the average point
- $20 per extra m², others held fixed
- Coefficients describe data, not causes
- R² 0.974: share of the spread explained
Try this
Watch gradient descent stall, explode, then settle
In a notebook, run the gradient-descent loop on the five flats twice over. First on raw area in m², from w = 25 and b = 200, with learning rates 0.0001, 0.0002 and 0.00021. Then on rescaled area with 0.2 and 1.1. Record the MSE at every step and plot all five runs on one chart with matplotlib (put the MSE axis on a log scale). Last, check the answer with np.linalg.lstsq on a table that has a column of 1s next to the areas.
You need: Python with numpy and matplotlib (pip install numpy matplotlib), or a free notebook such as Google Colab.
Look for
- The raw-unit runs, where the slope settles quickly and the intercept hardly moves.
- The learning rate where raw units tip from slow to exploding, near 0.000207.
- The rescaled run at 0.2 reaching an MSE of 5,000 within twenty steps.
- The same 20 and 500 from
lstsq.
The words, in plain language
- Residual and mean squared error
- A residual is actual minus predicted, for one row. The mean squared error, MSE, is the average of the squared residuals. Its square root is back in the label's units: a typical miss.
- Gradient descent and learning rate
- Gradient descent fits a model by repeated small steps: work out the gradient of the loss for every parameter, move each one a little against it, and repeat until the loss stops falling. The learning rate scales each step.
- Least squares and closed form
- Least squares picks the parameters with the smallest sum of squared residuals, which is also the smallest MSE. For a line the answer has a closed form: a formula you compute directly, with no steps.
- Coefficient and R²
- A coefficient is the weight on one feature: how much the prediction changes when that feature rises by 1 and the others stay the same. R² is the share of the label's spread around its average that the model explains: 1 is perfect, 0 is no better than the average.
Watch
- Gradient Descent, Step-by-StepStatQuest with Josh Starmer, on YouTubeA line's intercept and slope fitted by gradient steps, with the arithmetic of each step written out.
- Stanford CS229: Machine Learning, Linear Regression and Gradient Descent (Lecture 2, Autumn 2018)Andrew Ng, Stanford Online, on YouTubeA full university lecture on the same ground: the squared-error cost, gradient descent and the normal equations.
Read next
- CS229 Lecture NotesTengyu Ma and Andrew Ng, StanfordPart I derives the gradient-descent update and the normal equations for linear regression, with more maths than this lesson uses.
- Linear regression: Gradient descentGoogle for DevelopersLoss curves, and how a model's numbers move step by step as it trains.
- Linear Models: Ordinary Least Squaresscikit-learn documentationWhat LinearRegression minimises, how it's solved, and why near-copy features make its coefficients unstable.
Classical Machine Learning overviewSpotted a mistake? Tell us.