boosting系列算法

版权声明:本文为博主原创文章,转载请注明出处 https://blog.csdn.net/jingshuiliushen_zj/article/details/83350215

boosting是一种集成学习算法,由一系列基本分类器按照不同的权重组合成为一个强分类器,这些基本分类器之间有依赖关系。包括Adaboost算法、提升树、GBDT算法。

一、Adaboost算法

1、基本思想
通过两个问题:
1)如何更新样本权重D? 提高被弱分类器错分样本的权值,降低正分样本的权值,作为下一轮基本分类器的训练样本。
2)如何将弱分类器组合成强分类器? 加权多数表决,误差率小的分类器的权值大,使其在表决过程中起较大作用。
AdaBoost是个二分类算法。
2、推导
Adaboost的基本分类器的损失函数为指数函数,推导过程就是围绕最小化损失函数展开的。主要目的是推导出样本权值的更新公式、基本分类器的权值计算公式。
在这里插入图片描述
3、算法描述
在这里插入图片描述

二、提升树算法

1、基本思想
当Adaboost算法中的基本分类器是cart回归树时,就是提升树,同时,损失函数变为平方误差损失函数。在Adaboost算法中通过改变样本的权重来进行每一轮的基本分类器的学习,在提升树算法中,是通过上一轮学习的残差进行本轮的学习。

2、推导
和Adaboost算法一样,也是求最小化损失函数下第m颗树模型的参数 θ m \theta_m
在这里插入图片描述
f m ( x ) f_m(x) 是第m轮迭代的提升树模型, T ( x ; θ m ) T(x;\theta_m) 是第m轮的树模型。最后我们得到的模型是 f M ( x ) f_M(x)
通过推导发现,每一轮拟合的是上一轮的残差,通过最小化平方损失函数来拟合。

3、算法描述
在这里插入图片描述
一棵回归树: T ( x ; θ m ) = j = 1 J c j I ( x R j ) T(x;\theta_m)=\sum_{j=1}^J{c_jI( x \in R_j)}
4、举例
在这里插入图片描述

三、GBDT

1、基本思想
和提升树算法差不多,只不过GBDT的损失函数是不再是平方损失函数,而是一般的损失函数,所以用损失函数的负梯度来代替残差,也就是说,每一轮拟合的是上一轮损失函数的负梯度,拟合的过程也是求最小二乘回归树的过程。

2、算法描述
在这里插入图片描述
GBDT不再使用残差作为新的训练数据而是使用损失函数的梯度作为新的新的训练数据的y值,具体的来说就是使用损失函数对 f ( x ) f(x) 求梯度然后带入 f m 1 ( x ) f_{m-1}(x) 计算。

GBDT与提升树之间的关系:
 提升树模型每一轮的训练都是靠上次的预测结果与真实值的差值作为新的训练数据进行重新训练,GBDT则是将残差计算替换成了损失函数的梯度方向,将上一次的预测结果带入梯度中求出本轮的训练数据,这两种模型就是在生成新的训练数据时采用了不同的方法。
 boosting tree和GBDT,每一轮的树都是二层的(根节点+叶子节点),与一般的决策树的对比:
 在这里插入图片描述

四、XGBoost

XGBoost 就是对GBDT的实现,但是一般来说,gradient boosting 的实现是比较慢的,因为每次都要先构造出一个树并添加到整个模型序列中。而 XGBoost 的特点就是计算速度快,模型表现好.
表现快是因为它具有这样的设计:
1、Parallelization: 训练时可以用所有的 CPU 内核来并行化建树。
2、Distributed Computing : 用分布式计算来训练非常大的模型。
3、Out-of-Core Computing: 对于非常大的数据集还可以进行 Out-of-Core Computing。
4、Cache Optimization of data structures and algorithms: 更好地利用硬件。

xgboost和GBDT的不同之处? 参考:https://www.zhihu.com/question/41354392/answer/98658997

1、传统GBDT以CART作为基分类器,xgboost还支持线性分类器,传统GBDT在优化时只用到一阶导数信息,xgboost则对代价函数进行了二阶泰勒展开,同时用到了一阶和二阶导数。顺便提一下,xgboost工具支持自定义代价函数,只要函数可一阶和二阶求导。
2、xgboost在代价函数里加入了正则项,用于控制模型的复杂度。正则项里包含了树的叶子节点个数、每个叶子节点上输出的score的L2模的平方和。从Bias-variance tradeoff角度来讲,正则项降低了模型的variance,使学习出来的模型更加简单,防止过拟合,这也是xgboost优于传统GBDT的一个特性。
3、Shrinkage(缩减),相当于学习速率(xgboost中的eta)。xgboost在进行完一次迭代后,会将叶子节点的权重乘上该系数,主要是为了削弱每棵树的影响,让后面有更大的学习空间。实际应用中,一般把eta设置得小一点,然后迭代次数设置得大一点。(补充:传统GBDT的实现也有学习速率)
4、列抽样(column subsampling)。xgboost借鉴了随机森林的做法,支持列抽样,不仅能降低过拟合,还能减少计算,这也是xgboost异于传统gbdt的一个特性。
5、对缺失值的处理。对于特征的值有缺失的样本,xgboost可以自动学习出它的分裂方向。
6、xgboost工具支持并行。boosting不是一种串行的结构吗?怎么并行的?注意xgboost的并行不是tree粒度的并行,xgboost也是一次迭代完才能进行下一次迭代的(第t次迭代的代价函数里包含了前面t-1次迭代的预测值)。xgboost的并行是在特征粒度上的。我们知道,决策树的学习最耗时的一个步骤就是对特征的值进行排序(因为要确定最佳分割点),xgboost在训练之前,预先对数据进行了排序,然后保存为block结构,后面的迭代中重复地使用这个结构,大大减小计算量。这个block结构也使得并行成为了可能,在进行节点的分裂时,需要计算每个特征的增益,最终选增益最大的那个特征去做分裂,那么各个特征的增益计算就可以开多线程进行。
可并行的近似直方图算法。树节点在进行分裂时,我们需要计算每个特征的每个分割点对应的增益,即用贪心法枚举所有可能的分割点。当数据无法一次载入内存或者在分布式情况下,贪心算法效率就会变得很低,所以xgboost还提出了一种可并行的近似直方图算法,用于高效地生成候选的分割点。
7、内置交叉验证,XGBoost允许在每一轮boosting迭代中使用交叉验证。
调用:

import xgboost
watchlist = [(train_matrix, 'train'), (val_matrix, 'eval')]
model = xgboost.train(param, train_matrix, num_boost_round=num_round, evals=watchlist, early_stopping_rounds=early_stopping_rounds)

1、params 参数字典,里面包含着训练中的参数关键字和对应的值,形式是

init_param = {
        'max_depth': 8,
        'eta': 0.1,#学习速率
        'silent': 1,
        'seed': 13,
        'objective': 'binary:logistic',
        'eval_metric': 'auc',
        'scale_pos_weight': 2,
        'subsample': 0.8,#每棵树,随机采样的比例。
        'colsample_bytree': 0.7,#列采样
        'min_child_weight': 100,
        'max_delta_step': 20
    }

2、train_matrix:训练的数据
3、num_boost_round :迭代的轮数
4、evals :对evals列表中的元素在训练过程中进行评估。形式是evals = [(dtrain,’train’),(dval,’val’)],它使得我们可以在训练过程中观察验证集的效果。
5、early_stopping_rounds,早期停止次数 ,假设为100,验证集的误差迭代到一定程度在100次内不能再继续降低,就停止迭代。这要求evals 里至少有 一个元素,如果有多个,按最后一个去执行。返回的是最后的迭代次数(不是最好的)。如果early_stopping_rounds 存在,则模型会生成三个属性,bst.best_score,bst.best_iteration,和bst.best_ntree_limit

猜你喜欢

转载自blog.csdn.net/jingshuiliushen_zj/article/details/83350215