超参数优化:从基础到高级实践
立即解锁
发布时间: 2025-09-04 00:25:32 阅读量: 25 订阅数: 23 AIGC 


Kaggle竞赛实战指南
# 超参数优化:从基础到高级实践
## 常见机器学习算法的超参数
在机器学习中,不同的算法有各自需要调整的重要超参数,了解这些超参数对于构建优秀的模型至关重要。
### CatBoost超参数
| 超参数 | 取值范围 | 说明 |
| ---- | ---- | ---- |
| depth | 1 - 8 的整数 | 通常较高的值需要更长的拟合时间,且不一定能产生更好的结果 |
| learning_rate | 0.01 - 1.0 的实数,最好从对数均匀分布中采样 | 控制模型学习的步长 |
| random_strength | 从 1e - 9 到 10.0 对数线性采样的实数 | 指定评分分割的随机性水平 |
| bagging_temperature | 0.0 - 1.0 的实数 | 设置贝叶斯自助法 |
| border_count | 1 - 255 的整数 | 表示数值特征的分割 |
| l2_leaf_reg | 2 - 30 的整数 | L2 正则化的值 |
| scale_pos_weight | 0.01 - 10.0 的实数 | 表示正类的权重 |
### HistGradientBoosting超参数
| 超参数 | 取值范围 | 说明 |
| ---- | ---- | ---- |
| learning_rate | 0.01 - 1.0 的实数,通常从对数均匀分布中采样 | 控制模型学习的步长 |
| max_iter | 10 - 10,000 的整数 | 最大迭代次数 |
| max_leaf_nodes | 2 - 500 的整数 | 与 max_depth 相互作用,建议只设置其中一个,另一个设为 None |
| max_depth | 2 - 12 的整数 | 树的最大深度 |
| min_samples_leaf | 2 - 300 的整数 | 叶子节点的最小样本数 |
| l2_regularization | 0.0 - 100.0 的浮点数 | L2 正则化 |
| max_bins | 32 - 512 的整数 | 最大分箱数 |
虽然 Scikit - learn 的 HistGradientBoosting 与 LightGBM 或 XGBoost 没有太大区别,但它为在竞赛中实现梯度提升机(GBM)提供了不同的方式,并且在集成多个预测时(如混合和堆叠),HistGradientBoosting 构建的模型可能会有所贡献。
## 数据科学家的竞赛经验分享
与 Alberto Danese 的访谈为我们提供了宝贵的竞赛经验。Alberto Danese 是意大利信用卡和数字支付公司 Nexi 的数据科学主管,也是 Kaggle 竞赛大师。
### 竞赛偏好
他一直从事金融服务行业,处理结构化数据,因此更喜欢这类竞赛。他享受对数据有实际理解,并通过智能特征工程挖掘数据信息的过程。在技术上,他擅长使用经典的机器学习库,特别是梯度提升决策树,XGBoost、LightGBM、CatBoost 是他的首选。
### 竞赛方法
他在竞赛中会花大量时间探索数据,弄清楚主办方试图用机器学习解决的问题,而不是花太多时间调整特定的机器学习算法。在日常工作中,除了理解数据,还需要定义业务问题、寻找数据,以及将机器学习模型投入生产并管理其演变。
### 挑战竞赛
他提到了 TalkingData AdTracking Fraud Detection Challenge,这个竞赛推动他进行高效的特征工程,因为数据量巨大(超过 1 亿个标记行),减少计算时间对于测试不同方法至关重要。同时,他学会了如何最好地利用滞后/超前特征和其他窗口函数,在经典机器学习问题中创建时间序列。
### 对新手的建议
他认为新手常犯的错误是直接开始编码,而没有花足够的时间研究数据和理解问题。此外,他建议考虑团队合作,因为可以从合作中学习很多。
## 贝叶斯优化
在超参数优化中,网格搜索仅在实验空间有限时可行,因此通常会选择随机搜索优化或贝叶斯优化(BO)技术,后者需要更复杂的设置。
### 贝叶斯优化原理
贝叶斯优化的核心思想是优化代理函数(也称为替代函数),而不是真实的目标函数(网格搜索和随机搜索都直接优化真实目标函数)。当没有梯度、测试真实目标函数成本高昂,且搜索空间嘈杂复杂时,适合使用贝叶斯优化。
贝叶斯搜索平衡了探索和利用。开始时随机探索,训练替代函数,然后根据替代函数利用对预测器工作方式的初始近似知识,采样更有用的示例并最小化成本函数。通过使用先验知识,贝叶斯优化可以更快地达到最小化,减少评估次数。
贝叶斯优化使用获取函数来判断观察的前景。为了管理探索和利用之间的权衡,算法定义了一个获取函数,提供一个单一的度量来衡量尝试任何给定点的有用性。
### 实现方法
通常,贝叶斯优化由高斯过程驱动。当搜索空间具有平滑和可预测的响应时,高斯过程表现更好。当搜索空间更复杂时,可以使用树算法(如随机森林)或树结构 Parzen 估计器(TPEs)。
TPEs 不直接构建估计参数集成功的模型,而是估计定义参数最佳值的多元分布的参数,通过从概率分布中采样得出最佳参数集,而不是像高斯过程那样直接从机器学习模型中获取。
### 使用 Scikit - optimize 进行贝叶斯优化
Scikit - optimize(skopt)使用与 Scikit - learn 相同的 API,并广泛使用 NumPy 和 SciPy 函数。它基于高斯过程算法,维护良好,但有时需要跟上 Scikit - learn、NumPy 或 SciPy 的改进。
以下是使用 Scikit - optimize 对 LightGBM 模型进行贝叶斯优化的步骤:
#### 1. 加载必要的库
```python
# Importing core libraries
import numpy as np
import pandas as pd
from time import time
import pprint
import joblib
from functools import partial
# Suppressing warnings because of skopt verbosity
import warnings
warnings.filterwarnings("ignore")
# Classifiers
import lightgbm as lgb
# Model selection
from sklearn.model_selection import KFold
# Metrics
from sklearn.metrics import mean_squared_error
from sklearn.metrics import make_scorer
# Skopt functions
from skopt import BayesSearchCV
from skopt.callbacks import DeadlineStopper, DeltaYStopper
from skopt.space import Real, Categorical, Integer
```
#### 2. 加载数据
```python
# Loading data
X = pd.read_csv("../input/30-days-of-ml/train.csv")
X_test = pd.read_csv("../input/30-days-of-ml/test.csv")
# Preparing data as a tabular matrix
y = X.target
X = X.set_index('id').drop('target', axis='columns')
X_test = X_test.set_index('id')
# Dealing with categorical data
categoricals = [item for item in X.columns if 'cat' in item]
cat_values = np.unique(X[categoricals].values)
cat_dict = dict(zip(cat_values, range(len(cat_values))))
X[categoricals] = X[categoricals].replace(cat_dict).astype('category')
X_test[categoricals] = X_test[categoricals].replace(cat_dict).astype('category')
```
#### 3. 定义报告函数
```python
# Reporting util for different optimizers
def report_perf(optimizer, X, y, title="model", callbacks=None):
"""
A wrapper for measuring time and performance of optimizers
optimizer = a sklearn or a skopt optimizer
X = the training set
y = our target
title = a string label for the experiment
"""
start = time()
if callbacks is not None:
optimizer.fit(X, y, callback=callbacks)
else:
optimizer.fit(X, y)
d=pd.DataFrame(optimizer.cv_results_)
best_score = optimizer.best_score_
best_score_std = d.iloc[optimizer.best_index_].std_test_score
best_params = optimizer.best_params_
print((title + " took %.2f seconds, candidates checked: %d, best CV score: %.3f" + u" \u00B1"+" %.3f") %
(time() - start,
len(optimizer.cv_results_['params']),
```
0
0
复制全文
相关推荐









