Spec-Zone.ru › scikit-learn

Примечание

Перейти к концу для загрузки полного примера кода. или для запуска этого примера в вашем браузере через JupyterLite или Binder

Выбор модели Lasso: AIC-BIC / перекрестная проверка

Этот пример посвящен выбору модели для моделей Lasso, которые являются линейными моделями с L1-штрафом для задач регрессии.

Действительно, для выбора значения параметра регуляризации можно использовать несколько стратегий: через перекрестную проверку или с помощью критерия информации, а именно AIC или BIC.

В дальнейшем мы подробно обсудим различные стратегии.

# Authors: The scikit-learn developers
# SPDX-License-Identifier: BSD-3-Clause

Набор данных

В этом примере мы будем использовать набор данных о диабете.

from sklearn.datasets import load_diabetes

X, y = load_diabetes(return_X_y=True, as_frame=True)
X.head()
age sex bmi bp s1 s2 s3 s4 s5 s6
0 0.038076 0.050680 0.061696 0.021872 -0.044223 -0.034821 -0.043401 -0.002592 0.019907 -0.017646
1 -0.001882 -0.044642 -0.051474 -0.026328 -0.008449 -0.019163 0.074412 -0.039493 -0.068332 -0.092204
2 0.085299 0.050680 0.044451 -0.005670 -0.045599 -0.034194 -0.032356 -0.002592 0.002861 -0.025930
3 -0.089063 -0.044642 -0.011595 -0.036656 0.012191 0.024991 -0.036038 0.034309 0.022688 -0.009362
4 0.005383 -0.044642 -0.036385 0.021872 0.003935 0.015596 0.008142 -0.002592 -0.031988 -0.046641


Кроме того, мы добавляем некоторые случайные признаки к исходным данным, чтобы лучше проиллюстрировать выбор признаков, выполняемый моделью Lasso.

import numpy as np
import pandas as pd

rng = np.random.RandomState(42)
n_random_features = 14
X_random = pd.DataFrame(
    rng.randn(X.shape[0], n_random_features),
    columns=[f"random_{i:02d}" for i in range(n_random_features)],
)
X = pd.concat([X, X_random], axis=1)
# Show only a subset of the columns
X[X.columns[::3]].head()
age bp s3 s6 random_02 random_05 random_08 random_11
0 0.038076 0.021872 -0.043401 -0.017646 0.647689 -0.234137 -0.469474 -0.465730
1 -0.001882 -0.026328 0.074412 -0.092204 -1.012831 -1.412304 0.067528 0.110923
2 0.085299 -0.005670 -0.032356 -0.025930 -0.601707 -1.057711 0.208864 0.196861
3 -0.089063 -0.036656 -0.036038 -0.009362 -1.478522 1.057122 0.324084 0.611676
4 0.005383 0.021872 0.008142 -0.046641 0.331263 -0.185659 0.812526 1.003533


Выбор Lasso с помощью информационного критерия

LassoLarsIC предоставляет оценщик Lasso, который использует информационный критерий Акаике (AIC) или байесовский информационный критерий (BIC) для выбора оптимального значения параметра регуляризации alpha.

Перед обучением модели мы стандартизуем данные с помощью StandardScaler. Кроме того, мы измерим время обучения и настройки гиперпараметра alpha, чтобы сравнить со стратегией перекрестной проверки.

Сначала мы обучим модель Lasso с критерием AIC.

import time

from sklearn.linear_model import LassoLarsIC
from sklearn.pipeline import make_pipeline
from sklearn.preprocessing import StandardScaler

start_time = time.time()
lasso_lars_ic = make_pipeline(StandardScaler(), LassoLarsIC(criterion="aic")).fit(X, y)
fit_time = time.time() - start_time

Мы сохраняем метрику AIC для каждого значения alpha, используемого во время fit.

results = pd.DataFrame(
    {
        "alphas": lasso_lars_ic[-1].alphas_,
        "AIC criterion": lasso_lars_ic[-1].criterion_,
    }
).set_index("alphas")
alpha_aic = lasso_lars_ic[-1].alpha_

Теперь мы выполним тот же анализ, используя критерий BIC.

lasso_lars_ic.set_params(lassolarsic__criterion="bic").fit(X, y)
results["BIC criterion"] = lasso_lars_ic[-1].criterion_
alpha_bic = lasso_lars_ic[-1].alpha_

Мы можем проверить, какое значение alpha приводит к минимальному AIC и BIC.

def highlight_min(x):
    x_min = x.min()
    return ["font-weight: bold" if v == x_min else "" for v in x]


results.style.apply(highlight_min)
Критерий AIC Критерий BIC
alphas
45.160030 5244.764779 5244.764779
42.300343 5208.250639 5212.341949
21.542052 4928.018900 4936.201520
15.034077 4869.678359 4881.952289
6.189631 4815.437362 4831.802601
5.329616 4810.423641 4830.880191
4.306012 4803.573491 4828.121351
4.124225 4804.126502 4832.765671
3.820705 4803.621645 4836.352124
3.750389 4805.012521 4841.834310
3.570655 4805.290075 4846.203174
3.550213 4807.075887 4852.080295
3.358295 4806.878051 4855.973770
3.259297 4807.706026 4860.893055
3.237703 4809.440409 4866.718747
2.850031 4805.989341 4867.358990
2.384338 4801.702266 4867.163224
2.296575 4802.594754 4872.147022
2.031555 4801.236720 4874.880298
1.618263 4798.484109 4876.218997
1.526599 4799.543841 4881.370039
0.586798 4794.238744 4880.156252
0.445978 4795.589715 4885.598533
0.259031 4796.966981 4891.067109
0.032179 4796.662409 4894.853846
0.019069 4794.652739 4888.752867
0.000000 4796.626286 4894.817724


Наконец, мы можем построить график значений AIC и BIC для различных значений alpha. Вертикальные линии на графике соответствуют alpha, выбранному для каждого критерия. Выбранное alpha соответствует минимуму критерия AIC или BIC.

ax = results.plot()
ax.vlines(
    alpha_aic,
    results["AIC criterion"].min(),
    results["AIC criterion"].max(),
    label="alpha: AIC estimate",
    linestyles="--",
    color="tab:blue",
)
ax.vlines(
    alpha_bic,
    results["BIC criterion"].min(),
    results["BIC criterion"].max(),
    label="alpha: BIC estimate",
    linestyle="--",
    color="tab:orange",
)
ax.set_xlabel(r"$\alpha$")
ax.set_ylabel("criterion")
ax.set_xscale("log")
ax.legend()
_ = ax.set_title(
    f"Information-criterion for model selection (training time {fit_time:.2f}s)"
)
Information-criterion for model selection (training time 0.01s)

Отбор модели с помощью информационного критерия очень быстр. Он основан на вычислении критерия на предоставленном fit внутривыборочном множестве. Оба критерия оценивают ошибку обобщения модели на основе ошибки на обучающем множестве и штрафуют эту чрезмерно оптимистичную ошибку. Однако этот штраф основан на правильной оценке степеней свободы и дисперсии шума. Оба выводятся для больших выборок (асимптотические результаты) и предполагают, что модель верна, то есть что данные фактически генерируются этой моделью.

Эти модели также склонны к сбоям, когда задача плохо обусловлена (больше признаков, чем выборок). В этом случае требуется предоставить оценку дисперсии шума.

Выбор Lasso с помощью перекрёстной проверки

Модель Lasso может быть реализована с разными решателями: метод сопряжённого градиента и метод наименьших углов. Они отличаются по скорости выполнения и источникам численных ошибок.

В scikit-learn доступны два разных оценщика с интегрированной перекрёстной проверкой: LassoCV и LassoLarsCV, которые соответственно решают задачу с помощью метода сопряжённого градиента и метода наименьших углов.

В оставшейся части этого раздела мы представим оба подхода. Для обоих алгоритмов мы будем использовать стратегию перекрёстной проверки по 20 фолдам.

Lasso с помощью метода сопряжённого градиента

Начнём с настройки гиперпараметров с помощью LassoCV.

from sklearn.linear_model import LassoCV

start_time = time.time()
model = make_pipeline(StandardScaler(), LassoCV(cv=20)).fit(X, y)
fit_time = time.time() - start_time
import matplotlib.pyplot as plt

ymin, ymax = 2300, 3800
lasso = model[-1]
plt.semilogx(lasso.alphas_, lasso.mse_path_, linestyle=":")
plt.plot(
    lasso.alphas_,
    lasso.mse_path_.mean(axis=-1),
    color="black",
    label="Average across the folds",
    linewidth=2,
)
plt.axvline(lasso.alpha_, linestyle="--", color="black", label="alpha: CV estimate")

plt.ylim(ymin, ymax)
plt.xlabel(r"$\alpha$")
plt.ylabel("Mean square error")
plt.legend()
_ = plt.title(
    f"Mean square error on each fold: coordinate descent (train time: {fit_time:.2f}s)"
)
Mean square error on each fold: coordinate descent (train time: 0.27s)

Lasso с помощью метода наименьших углов

Начнём с настройки гиперпараметров с помощью LassoLarsCV.

from sklearn.linear_model import LassoLarsCV

start_time = time.time()
model = make_pipeline(StandardScaler(), LassoLarsCV(cv=20)).fit(X, y)
fit_time = time.time() - start_time
lasso = model[-1]
plt.semilogx(lasso.cv_alphas_, lasso.mse_path_, ":")
plt.semilogx(
    lasso.cv_alphas_,
    lasso.mse_path_.mean(axis=-1),
    color="black",
    label="Average across the folds",
    linewidth=2,
)
plt.axvline(lasso.alpha_, linestyle="--", color="black", label="alpha CV")

plt.ylim(ymin, ymax)
plt.xlabel(r"$\alpha$")
plt.ylabel("Mean square error")
plt.legend()
_ = plt.title(f"Mean square error on each fold: Lars (train time: {fit_time:.2f}s)")
Mean square error on each fold: Lars (train time: 0.07s)

Резюме подхода перекрёстной проверки

Оба алгоритма дают примерно одинаковые результаты.

Lars вычисляет траекторию решения только для каждой точки перегиба на траектории. В результате он очень эффективен, когда есть только несколько точек перегиба, что имеет место, если мало признаков или образцов. Также он может вычислить полную траекторию без установки каких-либо гиперпараметров. В противоположность этому, метод сопряжённого градиента вычисляет точки траектории на заранее заданной сетке (здесь мы используем значение по умолчанию). Таким образом, он более эффективен, если количество точек на сетке меньше, чем количество точек перегиба на траектории. Такая стратегия может быть интересной, если количество признаков действительно велико, и достаточно образцов для выбора в каждом из фолдов перекрёстной проверки. С точки зрения численных ошибок, при сильно коррелированных переменных Lars будет накапливать больше ошибок, в то время как алгоритм сопряжённого градиента будет только выборочно брать точки на траектории на заданной сетке.

Обратите внимание, как оптимальное значение альфа меняется для каждого фолда. Это демонстрирует, почему перекрёстная проверка со вложенными циклами — хорошая стратегия при попытке оценить эффективность метода, для которого параметр выбирается с помощью перекрёстной проверки: этот выбор параметра может быть не оптимальным для окончательной оценки на невидимом тестовом наборе.

Заключение

В этом руководстве мы представили два подхода к выбору лучшего гиперпараметра alpha: одна стратегия находит оптимальное значение alpha только используя обучающий набор и некоторые критерии информации, а другая стратегия основана на перекрёстной проверке.

В этом примере оба подхода работают аналогично. Выбор гиперпараметров на обучающем наборе демонстрирует свою эффективность с точки зрения вычислительной производительности. Однако он может использоваться только тогда, когда количество образцов достаточно велико по сравнению с количеством признаков.

Вот почему оптимизация гиперпараметров с помощью перекрёстной проверки является безопасной стратегией: она работает в различных сценариях.

Общее время выполнения скрипта: (0 минут 0,929 секунды)

Launch binder
Launch JupyterLite

Download Jupyter notebook: plot_lasso_model_selection.ipynb

Download Python source code: plot_lasso_model_selection.py

Download zipped: plot_lasso_model_selection.zip

Связанные примеры

Выбор модели Lasso с помощью критериев информации

Модели на основе l1 для разреженных сигналов

Траектории Lasso, Lasso-LARS и Elastic Net

Совместный отбор признаков с помощью многозадачного Lasso

© 2007–2025 The scikit-learn developers
Licensed under the 3-clause BSD License.
https://scikit-learn.org/1.6/auto_examples/linear_model/plot_lasso_model_selection.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API