SL Scikit-Learn Learn机器学习教程

Lesson 09

集成方法:组合弱学习器变强

单棵决策树容易过拟合,但把多棵树组合起来就能大幅提升泛化能力。本章涵盖 Bagging(随机森林)、Boosting(GBDT)和 Stacking 三大集成范式。

  • 预计时长55 分钟
  • 难度进阶
  • 前置章节第 08 章

本章细分学习地图

模块拆细学习单元完成后应产出掌握标准
Bagging自助采样、并行训练、投票/平均。随机森林代码。能说清 Bagging 降低方差的机制。
Boosting串行纠错、学习率、迭代次数。GBDT 代码。能说清 Boosting 降低偏差的机制。
Stacking元学习器、交叉验证生成元特征。Stacking 示例。能解释 Stacking 和投票的区别。
特征重要性feature_importances_ 解读。重要性排序输出。能解释不纯度重要性的偏差和替代方案。

学习目标

集成方法分类

1Bagging(并行)
2Boosting(串行)
3Stacking(元学习)

本章完成度

已完成 0/4

Bagging 与随机森林

Bagging(Bootstrap Aggregating)的核心思想:从训练集中有放回地采样多份子集,各自训练一棵树,最后投票(分类)或平均(回归)。

随机森林 = Bagging + 特征随机

每次分裂时只考虑随机选出的一部分特征,进一步降低树之间的相关性,减少方差。

为什么降方差

多个独立模型的平均预测比单个模型更稳定。自助采样和特征随机让每棵树尽可能"不同"。

from sklearn.datasets import load_wine
from sklearn.ensemble import RandomForestClassifier
from sklearn.model_selection import cross_val_score

X, y = load_wine(return_X_y=True)

rf = RandomForestClassifier(n_estimators=100, max_depth=5, random_state=42)
scores = cross_val_score(rf, X, y, cv=5)
print(f"随机森林准确率: {scores.mean():.3f} ± {scores.std():.3f}")

# 特征重要性
rf.fit(X, y)
feature_names = load_wine().feature_names
for name, imp in sorted(zip(feature_names, rf.feature_importances_),
                         key=lambda x: -x[1])[:5]:
    print(f"  {name}: {imp:.3f}")

Boosting 与 GBDT

Boosting 串行训练弱学习器,每一轮新模型重点关注前一轮预测错误的样本,逐步降低偏差。

算法核心思想sklearn 类
AdaBoost调整样本权重,让下一棵树关注难样本。AdaBoostClassifier
Gradient Boosting每棵树拟合前一轮的残差(梯度方向)。GradientBoostingClassifier
HistGradientBoosting基于直方图的快速 GBDT,大数据集首选。HistGradientBoostingClassifier
from sklearn.datasets import load_wine
from sklearn.ensemble import GradientBoostingClassifier
from sklearn.model_selection import cross_val_score

X, y = load_wine(return_X_y=True)

gb = GradientBoostingClassifier(
    n_estimators=100, learning_rate=0.1, max_depth=3, random_state=42
)
scores = cross_val_score(gb, X, y, cv=5)
print(f"GBDT 准确率: {scores.mean():.3f} ± {scores.std():.3f}")
学习率与树的数量

learning_rate 越小,每棵树的贡献越小,需要更多树(n_estimators 更大)才能收敛。通常 learning_rate=0.1 + n_estimators=100~500 是不错的起点。

Stacking

Stacking 用多个不同类型的模型(基学习器)做预测,再用一个元学习器(meta-learner)学习如何组合这些预测。

from sklearn.datasets import load_iris
from sklearn.ensemble import StackingClassifier, RandomForestClassifier
from sklearn.linear_model import LogisticRegression
from sklearn.svm import SVC
from sklearn.model_selection import cross_val_score

X, y = load_iris(return_X_y=True)

estimators = [
    ("rf", RandomForestClassifier(n_estimators=50, random_state=42)),
    ("svc", SVC(kernel="rbf", probability=True, random_state=42)),
]
stack = StackingClassifier(
    estimators=estimators,
    final_estimator=LogisticRegression(max_iter=1000),
    cv=5,
)
scores = cross_val_score(stack, X, y, cv=5)
print(f"Stacking 准确率: {scores.mean():.3f} ± {scores.std():.3f}")

Bagging vs Boosting 对比

维度Bagging(随机森林)Boosting(GBDT)
训练方式并行,互不依赖。串行,后一棵依赖前一棵。
降什么降方差(减少过拟合)。降偏差(提升拟合能力)。
对噪声更鲁棒。对噪声和离群点更敏感。
调参n_estimators、max_depth。n_estimators、learning_rate、max_depth。

练习题

第 1 题:随机森林中"特征随机"的作用是什么?

参考思路:让每棵树在不同特征子集上分裂,降低树之间的相关性,从而使集成的方差降得更低。如果每棵树都用最强特征分裂,树会很相似,集成效果有限。

第 2 题:GBDT 的 learning_rate 设得太大会怎样?

参考思路:每棵树的贡献过大,容易过拟合,且收敛不稳定。通常搭配较大的 n_estimators 使用较小的 learning_rate。

检查点

离开本章前,请确认:

  • 能解释 Bagging 降方差和 Boosting 降偏差的核心机制。
  • 能用 RandomForestClassifier 和 GradientBoostingClassifier 完成分类。
  • 能从 feature_importances_ 中解读并排序特征重要性。
  • 能说清 Stacking 与简单投票的区别。