12 交叉验证与模型选择
12.1 简介
在构建预测模型时,选择合适的模型至关重要。不同的模型可能会对同一数据集产生不同的预测效果,因此需要通过某些方法来评估和选择模型。交叉验证是一种常用的技术,用于评估模型的表现并避免过拟合。
12.2 交叉验证
交叉验证是一种将数据分成多个子集,并对每个子集分别进行训练和测试的技术。最常见的形式是K折交叉验证,其中数据被分成K个子集,每次使用一个子集作为测试集,其余的作为训练集。
在Python中,scikit-learn
提供了cross_val_score
函数来执行K折交叉验证。
from sklearn.datasets import make_regression
from sklearn.linear_model import LinearRegression
from sklearn.model_selection import cross_val_score
# 生成模拟数据
X, y = make_regression(n_samples=1000, n_features=10, noise=0.1, random_state=42)
# 构建线性回归模型
model = LinearRegression()
# 执行5折交叉验证
cv_scores = cross_val_score(model, X, y, cv=5)
print(f"Cross-validated scores: {cv_scores}")
print(f"Mean CV score: {cv_scores.mean():.2f}")
12.3 模型选择
模型选择的过程通常涉及在多个候选模型中选择一个表现最优的模型。可以基于交叉验证结果选择具有最高评分的模型。
假设我们在多项式回归模型之间进行选择,不同的多项式阶数代表不同的候选模型。
from sklearn.preprocessing import PolynomialFeatures
from sklearn.pipeline import make_pipeline
# 创建不同阶数的多项式回归模型
degrees = [1, 2, 3, 4]
models = [make_pipeline(PolynomialFeatures(degree), LinearRegression()) for degree in degrees]
# 选择最佳模型
best_score = float('-inf')
best_model = None
for model in models:
cv_scores = cross_val_score(model, X, y, cv=5)
if cv_scores.mean() > best_score:
best_score = cv_scores.mean()
best_model = model
print(f"Best model degree: {best_model.named_steps['polynomialfeatures'].degree}")
print(f"Best CV score: {best_score:.2f}")
12.4 模型的评估指标
在模型选择过程中,使用适当的评估指标来衡量模型的表现非常重要。常用的回归评估指标包括均方误差(MSE)、均方根误差(RMSE)和 值。对于分类任务,可以使用准确率、F1得分、ROC AUC等指标。
from sklearn.metrics import mean_squared_error, r2_score
# 假设我们已经训练了一个模型并进行了预测
model.fit(X, y)
y_pred = model.predict(X)
# 计算评估指标
mse = mean_squared_error(y, y_pred)
r2 = r2_score(y, y_pred)
print(f"Mean Squared Error: {mse:.2f}")
print(f"R^2: {r2:.2f}")
12.5 调参与模型选择
除了选择模型类型外,调参也是模型选择的一部分。不同模型的参数对模型的表现有显著影响,因此通常需要通过网格搜索或随机搜索来找到最佳参数组合。
在Python中,scikit-learn
提供了GridSearchCV
和RandomizedSearchCV
来进行超参数调优。
from sklearn.model_selection import GridSearchCV
# 定义模型和参数网格
param_grid = {'alpha': [0.1, 1.0, 10.0]}
ridge = Ridge()
# 网格搜索
grid_search = GridSearchCV(ridge, param_grid, cv=5)
grid_search.fit(X, y)
print(f"Best parameters: {grid_search.best_params_}")
print(f"Best CV score: {grid_search.best_score_:.2f}")