SVM 정규화 매개변수 조정

Beginner

This tutorial is from open-source community. Access the source code

소개

이 실험은 서포트 벡터 머신 (SVM) 을 이용한 분류에서 정규화 매개변수의 스케일링 효과를 보여줍니다. SVM 분류에서 우리는 다음 방정식에 대한 위험 최소화에 관심이 있습니다.

C \sum_{i=1, n} \mathcal{L} (f(x_i), y_i) + \Omega (w)

여기서:

  • C는 정규화의 양을 설정하는 데 사용됩니다.
  • L은 샘플과 모델 매개변수의 손실 함수입니다.
  • Ω는 모델 매개변수의 페널티 함수입니다.

VM 팁

VM 시작이 완료되면 왼쪽 상단 모서리를 클릭하여 Notebook 탭으로 전환하여 연습을 위한 Jupyter Notebook에 접근할 수 있습니다.

때때로 Jupyter Notebook 이 로드되는 데 몇 초가 걸릴 수 있습니다. Jupyter Notebook 의 제한으로 인해 작업의 유효성 검사는 자동화될 수 없습니다.

학습 중 문제가 발생하면 Labby 에 문의하십시오. 세션 후 피드백을 제공하면 문제를 신속하게 해결해 드리겠습니다.

라이브러리 가져오기 및 합성 데이터셋 생성

L1 및 L2 정규화에 적합한 합성 데이터셋을 생성하여 시작합니다.

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
from sklearn.datasets import make_classification
from sklearn.svm import LinearSVC
from sklearn.model_selection import validation_curve, ShuffleSplit

n_samples, n_features = 100, 300
X, y = make_classification(n_samples=n_samples, n_features=n_features, n_informative=5, random_state=1)

rng = np.random.RandomState(1)
y = np.sign(0.5 - rng.rand(n_samples))
X = rng.randn(n_samples, n_features // 5) + y[:, np.newaxis]
X += 5 * rng.randn(n_samples, n_features // 5)

L1 페널티 케이스

L1 케이스에서 이론적으로는 모델 일관성 (즉, 올바른 0 이 아닌 매개변수 집합과 그 부호를 찾는 것) 은 C를 조정하여 달성할 수 있습니다. 이 효과는 소수의 특징만이 모델에 정보가 되고 유용한 희소한 합성 데이터셋을 사용하여 보여줍니다.

model_l1 = LinearSVC(penalty="l1", loss="squared_hinge", dual=False, tol=1e-3)

Cs = np.logspace(-2.3, -1.3, 10)
train_sizes = np.linspace(0.3, 0.7, 3)
labels = [f"fraction: {train_size}" for train_size in train_sizes]

results = {"C": Cs}
for label, train_size in zip(labels, train_sizes):
    cv = ShuffleSplit(train_size=train_size, test_size=0.3, n_splits=50, random_state=1)
    train_scores, test_scores = validation_curve(
        model_l1, X, y, param_name="C", param_range=Cs, cv=cv
    )
    results[label] = test_scores.mean(axis=1)
results = pd.DataFrame(results)

fig, axes = plt.subplots(nrows=1, ncols=2, sharey=True, figsize=(12, 6))

## C 를 조정하지 않은 결과 플롯
results.plot(x="C", ax=axes[0], logx=True)
axes[0].set_ylabel("CV 점수")
axes[0].set_title("조정 없음")

## C 를 조정한 결과 플롯
for train_size_idx, label in enumerate(labels):
    results_scaled = results[[label]].assign(
        C_scaled=Cs * float(n_samples * train_sizes[train_size_idx])
    )
    results_scaled.plot(x="C_scaled", ax=axes[1], logx=True, label=label)
axes[1].set_title("C 를 n_samples 로 조정")

_ = fig.suptitle("L1 페널티로 C 조정 효과")

L2 페널티 케이스

l2 페널티로 유사한 실험을 반복할 수 있습니다. 이 경우 이론적으로 예측 일관성을 달성하기 위해 페널티 매개변수는 샘플 수가 증가함에 따라 일정하게 유지되어야 합니다.

model_l2 = LinearSVC(penalty="l2", loss="squared_hinge", dual=True)
Cs = np.logspace(-4.5, -2, 10)

labels = [f"fraction: {train_size}" for train_size in train_sizes]
results = {"C": Cs}
for label, train_size in zip(labels, train_sizes):
    cv = ShuffleSplit(train_size=train_size, test_size=0.3, n_splits=50, random_state=1)
    train_scores, test_scores = validation_curve(
        model_l2, X, y, param_name="C", param_range=Cs, cv=cv
    )
    results[label] = test_scores.mean(axis=1)
results = pd.DataFrame(results)

fig, axes = plt.subplots(nrows=1, ncols=2, sharey=True, figsize=(12, 6))

## C 를 조정하지 않은 결과 플롯
results.plot(x="C", ax=axes[0], logx=True)
axes[0].set_ylabel("CV 점수")
axes[0].set_title("조정 없음")

## C 를 조정한 결과 플롯
for train_size_idx, label in enumerate(labels):
    results_scaled = results[[label]].assign(
        C_scaled=Cs * float(n_samples * train_sizes[train_size_idx])
    )
    results_scaled.plot(x="C_scaled", ax=axes[1], logx=True, label=label)
axes[1].set_title("C 를 n_samples 로 조정")

_ = fig.suptitle("L2 페널티로 C 조정 효과")

요약

이 실험에서는 L1 및 L2 페널티에 대한 SVM 에서 정규화 매개변수를 조정하는 효과를 보여주었습니다. L1 페널티의 경우, 샘플 수로 C를 조정했을 때 교차 검증 오류가 테스트 오류와 가장 잘 상관 관계를 보였습니다. L2 페널티의 경우, C를 조정하지 않은 경우가 가장 좋은 결과를 보였습니다.