MediumClassic ML

Ridge Regression

Classic ML

Medium

Problem

Ridge regression (L2 regularization) adds a penalty term to the ordinary least squares objective to prevent overfitting. The regularization term shrinks the weights toward zero, which is especially useful when features are correlated or when the number of features is large relative to the number of samples.

Given a feature matrix X, a target vector y, and a regularization parameter lambda, compute the ridge regression weights using the closed-form solution.

Formula

w = (X^T X + \lambda I)^{-1} X^T y

Where I is the d x d identity matrix and lambda controls the regularization strength.

Return one float weight for each feature column.

Theory

Ridge regression is linear regression with L2 regularization. It adds a penalty term to the loss function that discourages large coefficient values, helping prevent overfitting.

L(\beta) = \sum_{i=1}^{n} (y_i - \hat{y}_i)^2 + \lambda \sum_{j=1}^{p} \beta_j^2

where:


Why Regularize?

Problem with ordinary least squares (OLS):

When features are correlated (multicollinearity) or when p > n (more features than samples), OLS:

Ridge solution:

The penalty term \lambda \sum_j \beta_j^2 shrinks coefficients toward zero, reducing variance at the cost of introducing some bias.


The Ridge Objective

In matrix notation:

L(\beta) = ||y - X\beta||^2 + \lambda ||\beta||^2

where:


The Closed-Form Solution

Taking the derivative and setting to zero:

\frac{\partial L}{\partial \beta} = -2X^T(y - X\beta) + 2\lambda\beta = 0

X^T X \beta + \lambda\beta = X^T y

(X^T X + \lambda I) \beta = X^T y

Ridge solution:

\hat{\beta} = (X^T X + \lambda I)^{-1} X^T y

The addition of \lambda I ensures the matrix is invertible, even when X^T X is singular.


Comparing to OLS

Ordinary Least Squares:

\hat{\beta}_{OLS} = (X^T X)^{-1} X^T y

Ridge Regression:

\hat{\beta}_{Ridge} = (X^T X + \lambda I)^{-1} X^T y

The difference is adding \lambda I to the diagonal of X^T X.


The Role of \lambda

Small \lambda (weak regularization):

Large \lambda (strong regularization):

Optimal \lambda:


Worked Example

Data: 3 samples, 2 features

X = \begin{bmatrix} 1 & 2 \\ 2 & 3 \\ 3 & 5 \end{bmatrix}, \quad y = \begin{bmatrix} 5 \\ 8 \\ 12 \end{bmatrix}

Step 1: Compute X^T X

X^T X = \begin{bmatrix} 1 & 2 & 3 \\ 2 & 3 & 5 \end{bmatrix} \begin{bmatrix} 1 & 2 \\ 2 & 3 \\ 3 & 5 \end{bmatrix} = \begin{bmatrix} 14 & 23 \\ 23 & 38 \end{bmatrix}

Step 2: Add \lambda I (let \lambda = 1)

X^T X + \lambda I = \begin{bmatrix} 14 & 23 \\ 23 & 38 \end{bmatrix} + \begin{bmatrix} 1 & 0 \\ 0 & 1 \end{bmatrix} = \begin{bmatrix} 15 & 23 \\ 23 & 39 \end{bmatrix}

Step 3: Compute X^T y

X^T y = \begin{bmatrix} 1 & 2 & 3 \\ 2 & 3 & 5 \end{bmatrix} \begin{bmatrix} 5 \\ 8 \\ 12 \end{bmatrix} = \begin{bmatrix} 57 \\ 94 \end{bmatrix}

Step 4: Solve (X^T X + \lambda I)\beta = X^T y

\begin{bmatrix} 15 & 23 \\ 23 & 39 \end{bmatrix} \beta = \begin{bmatrix} 57 \\ 94 \end{bmatrix}

Inverse: \det = 15 \times 39 - 23 \times 23 = 585 - 529 = 56

(X^T X + \lambda I)^{-1} = \frac{1}{56} \begin{bmatrix} 39 & -23 \\ -23 & 15 \end{bmatrix}

\hat{\beta} = \frac{1}{56} \begin{bmatrix} 39 & -23 \\ -23 & 15 \end{bmatrix} \begin{bmatrix} 57 \\ 94 \end{bmatrix}

= \frac{1}{56} \begin{bmatrix} 39 \times 57 - 23 \times 94 \\ -23 \times 57 + 15 \times 94 \end{bmatrix} = \frac{1}{56} \begin{bmatrix} 2223 - 2162 \\ -1311 + 1410 \end{bmatrix} = \frac{1}{56} \begin{bmatrix} 61 \\ 99 \end{bmatrix}

\hat{\beta} \approx \begin{bmatrix} 1.09 \\ 1.77 \end{bmatrix}


Geometric Interpretation

OLS: Find the point in the column space of X closest to y.

Ridge: Find the point that balances closeness to y (fitting the data) with staying close to the origin (small coefficients).

The ridge constraint ||\beta||^2 \leq t defines a sphere in coefficient space. Ridge finds the point on or inside this sphere that minimizes the residual sum of squares.


Bias-Variance Tradeoff

OLS:

Ridge:

Total error = Bias^2 + Variance

Ridge can achieve lower total error by trading off increased bias for reduced variance.


Ridge vs Lasso

Ridge (L2 regularization):

Lasso (L1 regularization):

Elastic Net:


Standardization

Important: Ridge penalizes coefficients, so features must be on the same scale.

Before fitting:

  1. Center features: subtract mean
  2. Scale features: divide by standard deviation

Without standardization, features with large values will have artificially small coefficients, receiving less penalty.

The intercept is typically not penalized and is computed separately after centering.


Choosing \lambda via Cross-Validation

Procedure:

  1. Choose a grid of \lambda values (e.g., 10^{-4} to 10^4, logarithmically spaced)
  2. For each \lambda:
    • Perform k-fold cross-validation
    • Compute average validation error
  3. Select \lambda with lowest validation error

Common choices:


SVD Solution

Using singular value decomposition X = U\Sigma V^T:

\hat{\beta} = V (\Sigma^2 + \lambda I)^{-1} \Sigma U^T y

This shows that ridge regression shrinks the contribution of small singular values more than large ones, stabilizing the solution.

Effective degrees of freedom:

df(\lambda) = \sum_{j=1}^{p} \frac{\sigma_j^2}{\sigma_j^2 + \lambda}

where \sigma_j are the singular values. As \lambda increases, effective degrees of freedom decreases.


Kernel Ridge Regression

For non-linear relationships, use the kernel trick:

\hat{y} = K(K + \lambda I)^{-1} y

where K is the kernel matrix: K_{ij} = k(x_i, x_j).

This allows ridge regression in infinite-dimensional feature spaces without explicitly computing the features.


Computational Complexity

Direct solution:

When n < p:

Iterative methods:


Ridge Regression for Classification

Ridge can be adapted for classification:

Approach 1: Use ridge regression directly with binary targets (0/1 or -1/+1). Not ideal but sometimes works.

Approach 2: Logistic regression with L2 penalty (ridge logistic regression):

L = -\sum_i [y_i \log p_i + (1-y_i) \log(1-p_i)] + \lambda ||\beta||^2

This is more principled for classification tasks.

Examples

Example 1

Input
X = [[1, 0], [0, 1]], y = [3, 5], lam = 1
Output
[1.5, 2.5]
Explanation
Adding the identity matrix doubles the diagonal before solving for the weights.

Example 2

Input
X = [[1, 1], [1, 2], [1, 3]], y = [3, 5, 7], lam = 0
Output
[1.0, 2.0]

Hints

  1. Create an identity matrix with the same width as X.
  2. Apply NumPy matrix multiplication in the same order as the closed-form equation.

Requirements

Constraints

Starter Code

import numpy as np

def ridge_regression(X: list, y: list, lam: float) -> list:
    """
    Returns the ridge-regression weight vector.
    """
    # Write code here
    pass

Test Cases

CaseMatches
Identity matrixExample 1public
With bias columnExample 2public