Xgboost原理

1.集成学习

所谓集成学习,是指构建多个分类器(弱分类器)对数据集进行预测,然后用某种策略将多个分类器预测的结果集成起来,作为最终预测结果。通俗比喻就是“三个臭皮匠赛过诸葛亮”,它要求每个弱分类器具备一定的“准确性”,分类器之间具备“差异性”。集成学习根据各个弱分类器之间有无依赖关系,分为Boosting和Bagging

Boosting

各分类器之间有依赖关系,必须串行,比如Adaboost、GBDT(Gradient Boosting Decision Tree)、Xgboost。
AdaBoost(Adaptive Boosting):前一个基本分类器分错的样本会得到加强,加权后的全体样本再次被用来训练下一个基本分类器。同时,在每一轮中加入一个新的弱分类器,直到达到某个预定的足够小的错误率或达到预先指定的最大迭代次数。

Bagging

各分类器之间没有依赖关系,可各自并行,比如随机森林(Random Forest)

2.树

首先xgboost就是由很多分类和回归树集成

分类树

有一堆人,我让你分出男女,你依靠头发长短将人群分为两拨,长发的为“女”,短发为“男,相当于你依靠一个指标“头发长短”将这群人进行了划分,形成了一个简单的决策树,而划分的依据是头发长短。但为什么要用“头发长短”划分?我还可以用“穿的鞋子是否是高跟鞋”,“有没有喉结”来划分,但我们应该根据哪个指标划分更好呢?很直接的判断是哪个分类效果更好则优先用哪个。所以,这时就需要一个评价标准来量化分类效果了。 直观上来说,如果根据某个标准分类人群后,纯度越高效果越好,比如说你分为两群,“女”那一群都是女的,“男”那一群全是男的,那这个效果是最好的。但有时实际的分类情况不是那么理想,所以只能说越接近这种情况,我们则认为效果越好。
评价标准:信息增益(ID3)、信息增益率(C4.5)、基尼系数(CART)等

回归树

分类树的样本输出(即响应值)是类的形式,而回归树的样本输出是数值的形式,是连续值。

3.xgboost

GBDT

xgboost本质上是一个GBDT,但是力争把速度和效率发挥到极致,所以叫X (Extreme) GBoosted。GBDT的原理很简单,就是所有弱分类器的结果相加等于预测值,然后下一个弱分类器去拟合误差函数对预测值的残差(这个残差就是预测值与真实值之间的误差)。

例子:年龄预测,假定训练集只有4个人:A,B,C,D,他们的年龄分别是14,16,24,26。其中A、B分别是高一和高三学生;C,D分别是应届毕业生和工作两年的员工。

如果是用一棵传统的回归决策树来训练,会得到如下图所示结果:


Xgboost原理_第1张图片
image

现在我们使用GBDT来做这件事,由于数据太少,我们限定叶子节点做多有两个,即每棵树都只有一个分枝,并且限定只学两棵树。

我们会得到如下图所示结果:


Xgboost原理_第2张图片
image

在第一棵树分枝和图1一样,由于A,B年龄较为相近,C,D年龄较为相近,他们被分为左右两拨,每拨用平均年龄作为预测值。

  • 此时计算残差(残差的意思就是:A的实际值 - A的预测值 = A的残差),所以A的残差就是实际值14 - 预测值15 = 残差值-1。
  • 注意,A的预测值是指前面所有树累加的和,这里前面只有一棵树所以直接是15,如果还有树则需要都累加起来作为A的预测值。

残差在数理统计中是指实际观察值与估计值(拟合值)之间的差。“残差”蕴含了有关模型基本假设的重要信息。如果回归模型正确的话, 我们可以将残差看作误差的观测值。

进而得到A,B,C,D的残差分别为-1,1,-1,1。

然后拿它们的残差-1、1、-1、1代替A B C D的原值,到第二棵树去学习,第二棵树只有两个值1和-1,直接分成两个节点,即A和C分在左边,B和D分在右边,经过计算(比如A,实际值-1 - 预测值-1 = 残差0,比如C,实际值-1 - 预测值-1 = 0),此时所有人的残差都是0。

残差值都为0,相当于第二棵树的预测值和它们的实际值相等,则只需把第二棵树的结论累加到第一棵树上就能得到真实年龄了,即每个人都得到了真实的预测值。

换句话说,现在A,B,C,D的预测值都和真实年龄一致了。Perfect!
A: 14岁高一学生,购物较少,经常问学长问题,预测年龄A = 15 – 1 = 14
B: 16岁高三学生,购物较少,经常被学弟问问题,预测年龄B = 15 + 1 = 16

C: 24岁应届毕业生,购物较多,经常问师兄问题,预测年龄C = 25 – 1 = 24
D: 26岁工作两年员工,购物较多,经常被师弟问问题,预测年龄D = 25 + 1 = 26

所以,GBDT需要将多棵树的得分累加得到最终的预测得分,且每一次迭代,都在现有树的基础上,增加一棵树去拟合前面树的预测结果与真实值之间的残差。

xgboost

如果不考虑工程实现、解决问题上的一些差异,xgboost与gbdt比较大的不同就是目标函数的定义。


Xgboost原理_第3张图片
image.png

目标函数分为三部分:

  • 损失函数

  • 正则项


    Xgboost原理_第4张图片
    image.png

    T 表示叶子节点的个数,w表示节点的数值(这是回归树的东西,分类树对应的是类别)

  • 常数项

xgboost与GBDT的区别

  • 目标函数通过二阶泰勒展开式做近似。传统GBDT在优化时只用到一阶导数信息,xgboost则对代价函数进行了二阶泰勒展开,同时用到了一阶和二阶导数。注:支持自定义代价函数,只要函数可一阶和二阶求导。
  • 定义了树的复杂度,即xgboost在代价函数里加入了正则项,用于控制模型的复杂度,正则项里包含了树的叶子节点个数、每个叶子节点上输出的score的L2模的平方和。代替了剪枝。
  • 分裂结点处通过结构打分和分割损失动态生长。结构分数代替了回归树的误差平方和。
  • 分裂结点特征分割点选取使用了近似算法-可并行的近似直方图算法。树节点在进行分裂时,我们需要计算每个特征的每个分割点对应的增益,即用贪心法枚举所有可能的分割点。当数据无法一次载入内存或者在分布式情况下,贪心算法效率就会变得很低,所以xgboost还提出了一种可并行的近似直方图算法,用于高效地生成候选的分割点。用于加速和减小内存消耗。
  • 可以处理稀疏、缺失数据(节点分裂算法能自动利用特征的稀疏性),可以学习出它的分裂方向,加快稀疏计算速度。
  • 列抽样(column subsampling)[传统GBDT没有]
  • 支持并行化处理。xgboost的并行是在特征粒度上的,在训练之前,预先对特征进行了排序,然后保存为block结构,后面的迭代中重复地使用这个结构,大大减小计算量。在进行节点的分裂时,需要计算每个特征的增益,最终选增益最大的那个特征去做分裂,那么各个特征的增益计算就可以开多线程进行,即在不同的特征属性上采用多线程并行方式寻找最佳分割点。
  • 传统GBDT以CART作为基分类器,xgboost还支持线性分类器,这个时候xgboost相当于带L1和L2正则化项的逻辑斯蒂回归(分类问题)或者线性回归(回归问题)。通过booster [default=gbtree]设置参数:gbtree: tree-based models/gblinear: linear models。

你可能感兴趣的:(Xgboost原理)