机器学习超参数搜索策略与贝叶斯优化简介
机器学习超参数搜索策略与贝叶斯优化简介
训练机器学习模型时,除算法选型外,超参数(树深度、学习率、正则系数等)往往决定最终效果。本文归纳常见超参数搜索策略——从固定配置、网格/随机搜索,到贝叶斯优化与 sklearn 内置 CV 估计器;说明各自原理、适用场景、落地成本与选型建议。不涉及特定业务系统,以表格分类与 scikit-learn 生态为主。
目录
- 1. 超参数与搜索策略是什么
- 2. 固定超参:人工配置基线
- 3. 网格搜索 Grid Search
- 4. 随机搜索 Random Search
- 5. 贝叶斯优化 Bayesian Optimization
- 6. sklearn 内置自动选参
- 7. 策略总览与对比
- 8. 何时用哪种策略
- 9. 落地成本与工程注意点
- 10. 实践配置示例
- 11. 小结
- 12. 参考与来源
1. 超参数与搜索策略是什么
| 概念 | 说明 |
|---|---|
| 超参数(Hyperparameter) | 训练之前由人设定的配置,不由梯度下降直接学习,如 max_depth、C、learning_rate |
| 模型参数(Parameter) | 训练过程中学到的权重、分裂点等,如逻辑回归系数、树节点阈值 |
| 超参数搜索 | 在候选组合中,用验证集或交叉验证指标选出较优超参的一套流程 |
| 搜索策略 | 如何生成、评估、筛选候选超参组合的方法(网格、随机、贝叶斯等) |
贝叶斯优化是超参数搜索的一种策略,不是新的算法类型;与网格搜索、随机搜索并列,解决「下一组该试什么参数」的问题。
2. 固定超参:人工配置基线
做法:在配置文件或代码中写死一组超参,训练时直接 fit,不做自动搜索。
1
2
3
4
5
6
7
8
from sklearn.ensemble import RandomForestClassifier
clf = RandomForestClassifier(
max_depth=8,
min_samples_leaf=5,
random_state=42,
)
clf.fit(X_train, y_train)
| 优点 | 缺点 |
|---|---|
| 零搜索成本,可复现性最好 | 未必接近最优,换数据集易失效 |
| 无额外依赖,调试简单 | 调参全靠经验,难以量化「还差多少」 |
适用:快速原型、基线对比、搜索空间极小且已有成熟默认值时。工程上常作为第一版;效果稳定后再考虑 CV 搜索。
3. 网格搜索 Grid Search
做法:对离散化的超参列表做穷举组合,每组用交叉验证打分,取最优。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
from sklearn.model_selection import GridSearchCV
from sklearn.ensemble import RandomForestClassifier
param_grid = {
"max_depth": [4, 8, 12],
"min_samples_leaf": [2, 5, 10],
}
search = GridSearchCV(
RandomForestClassifier(random_state=42),
param_grid,
cv=3,
scoring="f1",
n_jobs=-1,
)
search.fit(X_train, y_train)
print(search.best_params_, search.best_score_)
| 优点 | 缺点 |
|---|---|
| 简单、可复现、结果可解释 | 维度一多组合数指数爆炸 |
sklearn 原生 GridSearchCV | 连续超参需先离散化,粒度难兼顾 |
经验:单算法 2~3 个超参、每维 3~5 个候选时仍可控;超过 5 维通常改用随机搜索或贝叶斯优化。
4. 随机搜索 Random Search
做法:从超参分布中随机抽样固定次数(n_iter),每组做 CV 评估。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
from sklearn.model_selection import RandomizedSearchCV
from scipy.stats import randint, uniform
param_dist = {
"max_depth": randint(4, 16),
"min_samples_leaf": randint(2, 20),
"max_features": uniform(0.3, 0.7),
}
search = RandomizedSearchCV(
RandomForestClassifier(random_state=42),
param_dist,
n_iter=12,
cv=3,
scoring="f1",
random_state=42,
n_jobs=-1,
)
search.fit(X_train, y_train)
| 优点 | 缺点 |
|---|---|
| 高维时往往不比网格差(Bergstra & Bengio, 2012) | 不保证覆盖边界组合 |
| 易对连续超参采样 | 试验次数少时方差较大 |
| 实现简单,仍属 sklearn 生态 | 无「利用历史 trial 智能选下一组」 |
经验:搜索空间 3 维以上或含连续超参时,n_iter=10~30 + 3~5 折 CV 是工业界常见起点;小样本场景 n_iter=6~12 往往已够用。
5. 贝叶斯优化 Bayesian Optimization
做法:根据已有 trial 的观测结果,用代理模型(Surrogate Model)估计「哪组超参更可能更好」,再智能选择下一组试验点,在有限 trial 预算下尽量少试、多赚。
1
2
3
4
5
6
7
初始化若干随机 trial
↓
用 CV 指标评估 → 更新代理模型(如高斯过程、TPE)
↓
代理模型推荐下一组超参
↓
重复直至 trial 预算用尽 → 输出 best params
5.1 常见实现
| 库 | 代理模型 / 采样器 | 特点 |
|---|---|---|
| Optuna | TPE(Tree-structured Parzen Estimator)等 | 生态活跃,与 XGBoost/LightGBM 集成多 |
| Hyperopt | TPE、随机等 | 老牌贝叶斯优化库 |
| scikit-optimize | 高斯过程(GP) | 与 sklearn 风格接近,小维度表现好 |
| Ray Tune | 多种 scheduler | 分布式、大规模 trial |
Optuna 最小示例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import optuna
from sklearn.model_selection import cross_val_score, StratifiedKFold
from sklearn.ensemble import RandomForestClassifier
def objective(trial):
params = {
"max_depth": trial.suggest_int("max_depth", 4, 16),
"min_samples_leaf": trial.suggest_int("min_samples_leaf", 2, 20),
}
clf = RandomForestClassifier(**params, random_state=42)
cv = StratifiedKFold(n_splits=3, shuffle=True, random_state=42)
scores = cross_val_score(clf, X_train, y_train, cv=cv, scoring="f1")
return scores.mean()
study = optuna.create_study(direction="maximize")
study.optimize(objective, n_trials=30)
print(study.best_params, study.best_value)
5.2 优势与局限
| 优势 | 局限 |
|---|---|
| trial 预算有限时,通常比纯随机更高效 | 需额外依赖(Optuna 等) |
| 适合 5 个以上超参、单次 trial 较贵(大模型训练) | 要编写 objective、处理超时与落盘 |
| Kaggle、AutoML 平台常见 | 小搜索空间 + 少超参时性价比偏低 |
| trial 轨迹可解释性弱于网格,需额外记录 |
是不是「最近很通用」? 在工业界、竞赛、大规模 AutoML 中,贝叶斯优化 / Optuna 确实很常见;但在小样本、每模型只调 1~2 个超参、搜索空间很小的场景,随机搜索或小网格 + 3 折 CV 往往更简单、更稳,贝叶斯优势不明显。
6. sklearn 内置自动选参
部分估计器在单一或少数超参上提供解析解或内置 CV,无需外层 GridSearchCV:
| 估计器 | 自动选择的量 | 说明 |
|---|---|---|
LogisticRegressionCV | 正则 C(及 l1_ratio) | 沿 C 网格做 CV,零额外库 |
RidgeCV / LassoCV / ElasticNetCV | 正则强度 alpha | 线性模型常用 |
ElasticNetCV | alpha + l1_ratio | L1/L2 混合 |
GammaRegressor 等 GLM | 部分正则路径 | 视版本与族而定 |
示例——逻辑回归只调 C:
1
2
3
4
5
6
7
8
9
10
11
from sklearn.linear_model import LogisticRegressionCV
clf = LogisticRegressionCV(
Cs=10,
cv=3,
scoring="f1",
max_iter=1000,
random_state=42,
)
clf.fit(X_train, y_train)
print(clf.C_) # 每个类别或 OvR 下的最优 C
适用:超参维度极低(尤其线性模型正则项)时,优先用内置 CV,代码量小、无新依赖。
7. 策略总览与对比
| 策略 | 做法 | 新依赖 | 典型 trial 数 | 最适合 |
|---|---|---|---|---|
| 固定超参 | 人工写死 | 无 | 1 | 基线、默认值已验证 |
| 网格搜索 | 穷举离散组合 | 无(sklearn) | 各维候选数之积 | 2~3 维、候选少 |
| 随机搜索 | 随机抽样 n_iter 组 | 无(sklearn) | 10~30 | 3 维以上、含连续超参 |
| 贝叶斯优化 | 代理模型指导下一组 | Optuna 等 | 20~100+ | 5 维以上、trial 贵 |
| 内置 CV 估计器 | 估计器内部沿路径搜 | 无 | 内置网格 | 只调 C/alpha 等 |
8. 何时用哪种策略
1
2
3
4
5
6
7
8
9
10
11
超参几个?样本多大?trial 贵不贵?
│
├─ 0 个要搜(用默认)──────→ 固定超参
│
├─ 1 个(如 LR 的 C)──────→ LogisticRegressionCV 等内置 CV
│
├─ 2~3 个,离散候选少 ────→ GridSearchCV 或小网格
│
├─ 3 个以上 / 含连续分布 ──→ RandomizedSearchCV(n_iter=6~30)
│
└─ 5 个以上 / 单次训练很慢 ─→ Optuna 等贝叶斯优化
| 场景 | 推荐策略 |
|---|---|
| 表格小样本(数百级)、每算法 1~2 个超参 | 小网格或 RandomizedSearchCV(n_iter=6~12) + 3 折 CV |
| 类别不平衡二分类 | StratifiedKFold,scoring='f1' 或业务选定指标 |
| Kaggle / 大规模 GBDT 调参 | Optuna TPE,trial 30~100+ |
仅调正则 C | LogisticRegressionCV,不必上贝叶斯 |
| 统一 AutoML 平台、多算法多超参 | 贝叶斯优化 + 试验管理(落盘、剪枝、并行) |
9. 落地成本与工程注意点
| 维度 | sklearn 网格/随机 | 贝叶斯优化(Optuna) |
|---|---|---|
| 新依赖 | 无 | 需安装 Optuna / Hyperopt 等 |
| 代码量 | 小(param_grid + GridSearchCV) | 中(objective、study、回调) |
| 与 Pipeline 集成 | Pipeline + GridSearchCV,参数名 clf__max_depth | 在 objective 内构建 Pipeline,注意预处理只在训练折 fit |
| 数据泄漏 | CV 必须在训练折内 fit 预处理器 | 同上;禁止在全量数据上 fit 再 CV |
| 小样本 + 少超参 | 足够 | 性价比偏低 |
| 可解释性 | 网格结果一目了然 | 需导出 study.trials_dataframe() |
| 复现 | random_state | sampler 种子 + n_trials 固定 |
交叉验证通用建议:
- 分类:
StratifiedKFold,n_splits=3或5(样本极少时用 3) - 评分:
f1、roc_auc等按任务选择,与业务指标对齐 - 搜索应包在 Pipeline 内,使缩放、编码与模型在同一 CV 折内拟合
10. 实践配置示例
以下为通用模式(非特定项目配置):多算法并行时,可对每种算法只搜 1~2 个最关键超参,控制搜索空间。先看总览,再按算法展开各超参的作用。
| 算法 | 建议自动搜索的超参 | 推荐策略 |
|---|---|---|
| 逻辑回归 | C(启用 Elastic Net 时加 l1_ratio) | LogisticRegressionCV 或小网格 Cs=[0.01, 0.1, 1, 10] |
| 随机森林 | max_depth、min_samples_leaf | GridSearchCV(3×3)或 RandomizedSearchCV(n_iter≤12) |
| XGBoost / LightGBM | max_depth、learning_rate | RandomizedSearchCV 或 Optuna(trial 多时再上贝叶斯) |
| SVM | C、gamma | 小网格或随机搜索(gamma 常用 scale/auto 或 log 采样) |
10.1 逻辑回归
线性模型主要靠正则强度控制过拟合;树模型那套深度/叶样本数在此不适用。
| 超参数 | 作用 | 是否建议自动搜 | 说明 |
|---|---|---|---|
C | 正则强度的倒数:越大惩罚越弱,模型越易拟合训练数据 | 优先 | 最该搜的旋钮;过小易欠拟合,过大易过拟合 |
l1_ratio | Elastic Net 中 L1 与 L2 的比例(0≈纯 L2,1≈纯 L1) | 优先(若启用 Elastic Net) | L1 倾向稀疏选特征,L2 平滑缩系数 |
penalty | l2 / l1 / elasticnet | 一般不搜 | 当作策略开关,不宜与 C 混成大网格 |
max_iter | 求解最大迭代次数 | 否 | 设足够大即可,不参与优化目标 |
class_weight | 类别权重(如 balanced) | 可选 | 多固定 balanced;或只搜 None vs balanced |
solver | 优化求解器 | 否 | Elastic Net 常用 saga |
建议搜索空间(示例):
| 超参数 | 建议范围 / 取值 |
|---|---|
C | 0.01 ~ 10(对数刻度,如 [0.01, 0.1, 1, 10]) |
l1_ratio | [0.1, 0.3, 0.5, 0.7, 0.9](仅 Elastic Net) |
推荐实现:LogisticRegressionCV + StratifiedKFold(n_splits=3),scoring='f1'(或任务选定指标)。
10.2 随机森林
随机森林无 L1/L2,靠树结构约束防过拟合;小样本下优先调深度与叶节点最小样本数。
| 超参数 | 作用 | 是否建议自动搜 | 说明 |
|---|---|---|---|
max_depth | 单棵树最大深度;越深表达能力越强、越易过拟合 | 优先 | 控制整体复杂度的主旋钮 |
min_samples_leaf | 叶节点最少样本数;越大叶子越「钝」、越不易过拟合 | 优先 | 小样本防过拟合的核心结构参数 |
min_samples_split | 内部节点再分裂所需最少样本 | 次要 | 与 min_samples_leaf 相关,通常二选一优先即可 |
n_estimators | 森林中树的数量 | 次要 | 增大通常更稳,收益递减;可固定较大值 |
max_features | 每棵树分裂时使用的特征子集比例/个数 | 可选 | 常用 sqrt;影响树间多样性 |
class_weight | 类别权重 | 可选 | 多固定 balanced |
n_jobs | 并行线程数 | 否 | 只影响速度,不影响模型质量 |
建议搜索空间(示例):
| 超参数 | 建议范围 |
|---|---|
max_depth | [8, 12, 16, 20, None] |
min_samples_leaf | [3, 5, 10, 20] |
n_estimators | [200, 300, 500](可选扩展) |
推荐实现:RandomizedSearchCV,n_iter 限制在 10~20,scoring='f1'。
10.3 XGBoost / LightGBM
提升树同时受树深、步长、轮数、采样与正则影响。首轮通常只搜对偏差–方差影响最大的 max_depth 与 learning_rate;树棵数可用早停在最终 fit 阶段决定。
| 超参数 | 作用 | 是否建议自动搜 | 说明 |
|---|---|---|---|
max_depth | 单棵弱学习器最大深度;越深越易捕捉交互、越易过拟合 | 优先 | 控制单树复杂度,对效果影响大 |
learning_rate | 每轮提升的步长;越小需更多树、通常更稳 | 优先 | 深度定后影响收敛与泛化 |
n_estimators | 提升轮数 / 树棵数 | 优先(或与早停配合) | 可固定较大上限,由早停定有效树数 |
min_child_weight | 叶节点最小样本权重(Hessian)和;越大越保守 | 次要 | 类似 RF 的叶约束,抑制过深分裂 |
subsample | 每轮行采样比例 | 次要 | 小于 1 时引入随机性,减轻过拟合 |
colsample_bytree | 每棵树列采样比例 | 次要 | 特征多时常用 0.6~0.9 |
reg_lambda | L2 正则系数 | 次要 | 平滑叶权重 |
reg_alpha | L1 正则系数 | 可选 | 促进稀疏;默认常为 0 |
gamma(XGB)/ min_split_gain(LGBM) | 分裂所需最小损失下降 | 可选 | 越大越不易分裂 |
scale_pos_weight | 正负样本权重比 | 一般不搜 | 宜由训练集正负比动态计算 |
tree_method / n_jobs | 实现与并行 | 否 | 不参与模型质量优化 |
建议搜索空间(示例):
| 超参数 | 建议范围 |
|---|---|
max_depth | [4, 6, 8, 10] |
learning_rate | [0.05, 0.1, 0.2] |
n_estimators | [100, 200, 300](若不用早停) |
推荐实现:小范围 RandomizedSearchCV;样本量与 trial 预算大时再上 Optuna。与早停联用时:CV 内固定 n_estimators,最终 fit 再开早停定有效树数。
10.4 SVM
| 超参数 | 作用 | 是否建议自动搜 | 说明 |
|---|---|---|---|
C | 软间隔惩罚:越大越不容错、边界越贴训练点 | 优先 | 与 LR 的 C 同类:正则强弱 |
gamma | RBF 等核的影响半径;越大决策边界越「尖」、越易过拟合 | 优先(核 SVM) | 常用 scale / auto,或 log 刻度采样 |
kernel | linear / rbf / poly 等 | 一般不搜或少搜 | 当作模型族选择,不宜与 C/gamma 盲目全组合 |
class_weight | 类别权重 | 可选 | 不平衡时可固定 balanced |
建议搜索空间(示例):C 取对数网格(如 [0.1, 1, 10]);gamma 用 ['scale', 'auto'] 或 log 采样。空间稍大时优先 RandomizedSearchCV。
10.5 通常不参与搜索的参数
以下宜固定为配置项,不宜纳入超参搜索网格:
| 类别 | 参数示例 | 原因 |
|---|---|---|
| 可复现性 | random_state | 固定种子保证可复现 |
| 工程性能 | n_jobs、tree_method | 与模型质量无关 |
| 数据管线 | 特征工程开关、enable_categorical | 属数据策略,应与模型超参分离 |
| 业务策略 | 类别平衡采样比、scale_pos_weight 计算方式 | 宜有独立逻辑,避免与结构超参搅在一起 |
| 收敛控制 | max_iter(LR) | 设足够大即可 |
10.6 CV 配置与选型结论
统一 CV 配置示例:
1
2
3
4
from sklearn.model_selection import StratifiedKFold
cv = StratifiedKFold(n_splits=3, shuffle=True, random_state=42)
# scoring="f1" # 二分类不平衡时常用
综合选型结论:
- 搜索空间小、每模型 1~2 个超参:不必上贝叶斯;
sklearn内置 CV / 小网格 /RandomizedSearchCV更简单、够用。 - 仅
sklearn即可覆盖多数表格学习场景,零新依赖。 - 待扩展到每算法 5 个以上超参或统一 AutoML 平台时,再引入 Optuna 等贝叶斯优化不迟。
- 首轮优先旋钮:LR 的
C→ 树模型的max_depth→ RF 的min_samples_leaf/ GBDT 的learning_rate。
11. 小结
| 要点 | 结论 |
|---|---|
| 贝叶斯优化是什么 | 一种超参数搜索策略,用历史 trial 建代理模型、智能选下一组参数 |
| 与网格/随机的差 | 网格穷举、随机无记忆;贝叶斯利用历史、trial 少时更高效 |
| 是否最近很通用 | 工业界/竞赛常见;小空间少超参时优势不明显 |
| 零依赖首选 | GridSearchCV、RandomizedSearchCV、*CV 内置估计器 |
| 何时上 Optuna | 超参维度高、trial 成本高、需要试验管理与剪枝 |
| 工程底线 | Pipeline + CV 防泄漏;random_state 保复现 |
12. 参考与来源
| 资源 | 链接 |
|---|---|
| scikit-learn Model selection | https://scikit-learn.org/stable/model_selection.html |
| GridSearchCV | https://scikit-learn.org/stable/modules/generated/sklearn.model_selection.GridSearchCV.html |
| RandomizedSearchCV | https://scikit-learn.org/stable/modules/generated/sklearn.model_selection.RandomizedSearchCV.html |
| LogisticRegressionCV | https://scikit-learn.org/stable/modules/generated/sklearn.linear_model.LogisticRegressionCV.html |
| Optuna 文档 | https://optuna.readthedocs.io/ |
| Bergstra & Bengio, Random Search for Hyper-Parameter Optimization | https://jmlr.org/papers/v13/bergstra12a.html |
