【sklearn】GradientBoosting(GBDT)
GBDT
- GBDT
- 1. 原理改进及特点
- 2. 导包 & 数据
- 3. sklearn.ensemble.GradientBoostingRegressor
- 3.1 参数
- 3.2 接口使用
- 4. sklearn.ensemble.GradientBoostingClassifier
- 4.1 参数
- 4.2 接口使用
GBDT
1. 原理改进及特点
- GBDT的弱评估器一定是回归器;
GBDT通过sigmoid或softmax函数输出分类结果;
AdaBoost、随机森林, 执行回归任务则弱评估器是回归器, 执行分类任务则弱评估器是分类器。 - GBDT的损失函数可用任意可微函数;
不局限于固定或单一的损失函数。
AdaBoost损失函数知识点未整理 - ⭐GBDT通过拟合残差影响后续弱评估器结构;
每次用于建立弱评估器的拟合目标是样本X和当下集成输出H(xi)与真实标签y的差异(y - H(xi) ), 称为残差;
AdaBoost修改样本权重, 拟合目标是真实标签y。 - GBDT建树前允许对样本和特征进行抽样;
GBDT加入随机森林中随机抽样的思想, 增大评估器的独立性(因此可有袋外数据集);
Boosting算法不会大规模依赖Bagging的方式降低方差,但其输出结果是弱评估器结果的加权求和,因此Boosting原则上也可获得由“平均”带来的小方差红利。
当弱评估器表现不稳定时,采用与随机森林相似的方式可以进一步增加Boosting算法的稳定性。
2. 导包 & 数据
from sklearn.ensemble import GradientBoostingClassifier
from sklearn.ensemble import GradientBoostingRegressor
from sklearn.model_selection import cross_validate, KFold
from sklearn.datasets import load_digits
data = load_digits()
X = data.data
y = data.target
# 定义交叉验证方式
cv = KFold(n_splits=5, shuffle=True, random_state=1)
print(X.shape,y.shape)
'''
(1797, 64) (1797,)
'''
3. sklearn.ensemble.GradientBoostingRegressor
3.1 参数
【sklearn】Adaboost 参考建树过程原理
'''
n_estimators 迭代次数,最终形成弱评估器数量
learning_rate 学习率η
'''
'''
init 输入计算初始预测结果H0的评估器对象
H1(xi)=H0(xi)+η*ф1*f1(xi) H0值需要单独确定
输入None或默认 类似输入随机数
输入字符串"zero" 代表H0=0开始迭代
输入评估器
具备fit、predict_proba功能
如决策树、逻辑回归等可以输出概率的模型
GBR().fit(X,y).init_ 返回查看H0
一般不主动调节init,算力足够超参数搜索可调节。
'''
'''
loss 回归器中的损失函数 https://www.bilibili.com/video/BV1AZ4y1Z79H
"squared_error"默认值 回归的平方误差,适用于预测离群值
"absolute_error" 回归的绝对误差,适用于排除离群值影响
"huber" 以上两者结合,适用于没有偏好
alpha 决定阈值,默认0.9
"quantile" 分位数回归中的弹球损失pinball_loss
alpha 公式中辅助计算损失函数的输出结果,默认0.9
.loss_ 查看损失函数对象
'''
3.2 接口使用
gbr = GradientBoostingRegressor(random_state=1412) # 默认100弱评估器
# https://blog.csdn.net/qq_45249685/article/details/125937140
result_gbdt = cross_validate(gbr
,X,y
,cv = cv
# 评估指标 负根均方误差
,scoring="neg_root_mean_squared_error"
,return_train_score=True # 返回验证集交叉验证分数
,verbose=True # 打印建模流程
,n_jobs=-1 # 调用所有cpu
)
'''
[Parallel(n_jobs=-1)]: Using backend LokyBackend with 8 concurrent workers.
[Parallel(n_jobs=-1)]: Done 2 out of 5 | elapsed: 3.1s remaining: 4.6s
[Parallel(n_jobs=-1)]: Done 5 out of 5 | elapsed: 3.1s finished
'''
result_gbdt
'''
{'fit_time': array([0.77227807, 0.76629114, 0.77031326, 0.74335098, 0.7691946 ]),
'score_time': array([0.00099397, 0.00099778, 0.00199771, 0.00099778, 0.00202942]),
'test_score': array([-1.17380397, -1.23704352, -1.18860127, -1.19422147, -1.22940202]),
'train_score': array([-0.87929556, -0.86166957, -0.85336338, -0.90142607, -0.87496085])}
'''
def RMSE(result, name):
return abs(result[name].mean()) # 不该**0.5吗??
# abs(result_gbdt['test_score'])**0.5
RMSE(result_gbdt, 'test_score')
'''
1.2046144510500025
'''
4. sklearn.ensemble.GradientBoostingClassifier
4.1 参数
'''
GBDT所有弱评估器都是回归树,分类问题借助softmax实现
多分类任务时,要求迭代次数n_estimators=10,多分类标签数n_classes个,实际建立10*n_classes个弱评估器
n_estimators 实际迭代次数
GBC().fit(x,y).n_estimators_ 查看
estimators_ 实际建立弱分类器数
GBC().fit(x,y).estimators_.shape 返回(n_estimators, n_classes),(迭代次数,每次迭代建立弱评估器数)
loss 分类器中的损失函数
"deviance" 默认值,交叉熵损失
"exponential" 指数损失,AdaBoost也使用,相当于执行没有权重调整的AdaBoost
都分别包含二分类损失函数和多分类损失函数
'''
4.2 接口使用
clf = GradientBoostingClassifier(n_estimators=10
,random_state=1)
result_clf = cross_validate(clf
,X,y
,cv = cv
,return_train_score=True
,verbose=True
,n_jobs=-1
)
'''
[Parallel(n_jobs=-1)]: Using backend LokyBackend with 8 concurrent workers.
[Parallel(n_jobs=-1)]: Done 2 out of 5 | elapsed: 2.8s remaining: 4.3s
[Parallel(n_jobs=-1)]: Done 5 out of 5 | elapsed: 2.9s finished
'''
# 分类默认用准确率评估
print(result_clf['train_score'].mean(),
result_clf['test_score'].mean())
'''
0.9600722220125183 0.9037310430207366
'''
clf.fit(X,y).estimators_.shape
'''
(10, 10)
'''