文章目录
一、系列文章
本篇主要顺着作者Tianqi Chen的PPT为思路来介绍(参考1),他的PPT和论文是XGboost的源头,把他的论文和PPT啃下来,XGboost就一定没问题(不要怕英文水平差的问题)
- XGboost可以说是在前面基础算法的基础上发展过来的,Boost,GBDT文章既是经典思想不能错过,也是XGboost的基础
甚至可以这样概括
X ​ G ​ B o o s t = e X t r e m e + G B D T = e X t r e m e + ( G r a d i e n t + B D T ) = e X t r e m e + G r a d i e n t + ( B o o s t i n g + D e c i s i o n T r e e ) \begin{aligned} X\!G\!Boost&=eXtreme+GBDT\\ &=eXtreme+(Gradient+BDT) \\ &=eXtreme+Gradient+(Boosting+DecisionTree) \end{aligned} XGBoost=eXtreme+GBDT=eXtreme+(Gradient+BDT)=eXtreme+Gradient+(Boosting+DecisionTree)
B o o s t i n g → B D T → G B D T → X ​ G ​ B o o s t Boosting \to BDT \to GBDT \to X\!G\!Boost Boosting→BDT→GBDT→XGBoost - Xgboost是通过前面基础一步步过来的(这样好理解)
二、 监督学习回顾(Review of key concepts of supervised learning)
1> 基本概念
监督学习需要有训练样本和标签,给定一个新的
x
i
x_{i}
xi得到预测的
y
^
\hat{y}
y^是训练的模型的目的。不同的模型,
y
^
\hat{y}
y^有着不同的形式,线性回归是一个连续值,逻辑回归是预测正例概率和负例的概率,但是这些模型都是学习对应的参数,有了模型的参数
w
w
w,就能够得到模型的预测结果
2> 目标函数
目标函数是经验损失与正则化项的加和
3.
L
(
Θ
)
L(\Theta)
L(Θ)衡量训练样本预测值和真实输出的误差,
Ω
(
Θ
)
\Omega(\Theta)
Ω(Θ)衡量模型的复杂度,正则化项主要是从模型的学习参数
w
w
w着手,
L
2
=
λ
∣
∣
w
∣
∣
2
L_{2}= \lambda||w||^2
L2=λ∣∣w∣∣2范数和
L
1
=
λ
∣
∣
w
∣
∣
1
L_{1}=\lambda||w||_{1}
L1=λ∣∣w∣∣1范数可以看到只与参数
w
w
w有关
4. 同时参数 模型以及正则化的分离一定程度上带来比较好的工程意义
3> Bias and Variance Trade-off
在之前的文章中提到关于Bias Variance Trade-off
目标函数中通常会有经验损失和正则化项。
5.
L
(
Θ
)
L(\Theta)
L(Θ)优化的效果是使得训练样本的误差尽量的减小,bias更小逼近最真实的模型基本分布,但是往往会把训练样本的噪声等都学到,使得模型更加复杂
6.
Ω
(
Θ
)
\Omega(\Theta)
Ω(Θ)的作用是模型尽量简单,使模型更加稳健,使得方差更小但是相对来说会增加训练样本的误差,所以两者是需要权衡使模型泛化能力更强
三、 回归树及集成(模型参数)
1> CART树
回归树的定义实际上就是:有哪些叶子节点(回归树的结构),以及叶子节点的均值(每个叶子节点的输出值),这个对理解XGboost 树模型的定义很关键
一棵树的决策难免有失误,很多树的组合集成却能达到很好的效果,分类树的集合就是随机森林,回归树的集成就是GBDT
集成的优点:
集成方法在大多数数据挖掘的比赛中得到了广泛的应用,得益于不需要数据幅度缩放,良好的可扩展性等。
2> 集成学习目标函数的定义
经验损失:
正则化项定义:
可以联系上面对目标函数的定义,目标函数 = 经验损失+ 正则化项
- 集成学习中已经不是学习模型的参数 w w w,而是学习每一棵树,每一棵树是由什么参数决定的,树的结构和叶子节点的输出(类似前面对树模型的定义)
- 树的复杂度控制,在于树的分裂次数(可以理解为叶子节点的个数)
四、XGboost
1> 目标函数及学习方法
- 目标函数: ∑ i = 1 n l ( y i , y i ^ ) \sum_{i=1}^{n}l(y_{i},\hat{y_{i}}) ∑i=1nl(yi,yi^)经验损失的泛化表示(可以表示很多的常规经验损失例如:平方损失等), ∑ k Ω ( f k ) \sum_{k}\Omega(f_{k}) ∑kΩ(fk)是每一颗树的正则化之和
- 学习方法采用前向分布计算,基于前面的GBDT可以看到,t时刻的决策树的构成,是等于前面t-1时刻决策树+此时基于残差学习到的一棵树
- 可以得到XGboost的第t棵树构造的时候,目标函数
O b j ( t ) = ∑ i = 1 n l ( y i , y i ^ ( t − 1 ) + f t ( x i ) ) + Ω ( f t ) + c o n s t a n t Obj^{(t)} = \sum_{i=1}^{n}l(y_{i},\hat{y_{i}} ^{(t-1)} + f_{t}(x_{i})) + \Omega(f_{t})+ constant Obj(t)=i=1∑nl(yi,yi^(t−1)+ft(xi))+Ω(ft)+constant
constant 代表前t-1树的正则项之和,已经在前n-1时刻优化得到,所以是常量
y i ^ ( t − 1 ) \hat{y_{i}} ^{(t-1)} yi^(t−1) 是前t-1时刻的预测也是常量,所以变量只有 f t ( x i ) f_{t}(x_{i}) ft(xi)
2> 二阶泰勒展开误差损失
- 取经验损失关于
y
i
^
(
t
−
1
)
\hat{y_{i}} ^{(t-1)}
yi^(t−1) 的一阶导数和二阶导数,忽略高阶导数项(根据泰勒展开式如图)
g i = ∂ y ^ ( t − 1 ) l ( y i , y ^ ( t − 1 ) ) , h i = ∂ y ^ ( t − 1 ) 2 l ( y i , y ^ ( t − 1 ) ) g_i=\partial_{\hat{y}^{\left(t-1\right)}}l\left(y_i,\hat{y}^{\left(t-1\right)}\right),h_i=\partial^2_{\hat{y}^{\left(t-1\right)}}l\left(y_i,\hat{y}^{\left(t-1\right)}\right) gi=∂y^(t−1)l(yi,y^(t−1)),hi=∂y^(t−1)2l(yi,y^(t−1)) - 得到最终的近似目标函数
- 可以看到如果训练误差是均方误差,会得到我们熟悉的形式
- 是对第t颗树的优化时,前t-1颗树结构是已经优化出来了的,凡是涉及到前t-1颗树的东西,都是一个常数可以进一步化简得到
3> 正则化项
前面说明了描述集成树的复杂度用叶子节点的个数,XGboost中选择
- 叶子节点的个数(T)
- 叶子节点的输出 作为复杂度度量的基本点(
w
w
w)
所以: Ω ( f ) = γ T + 1 2 λ ∥ w ∥ 2 = γ T + 1 2 λ ∑ j = 1 T w j 2 \Omega\left(f\right)=\gamma T+\frac{1}{2}\lambda\|w\|^2=\gamma T+\frac{1}{2}\lambda\sum_{j=1}^T w_j^2 Ω(f)=γT+21λ∥w∥2=γT+21λ∑j=1Twj2。 - 所以目标函数:
O b j ( t ) = ∑ i = 1 n [ g i f t ( x i ) + 1 2 h i f t 2 ( x i ) ] + γ T + 1 2 λ ∑ j = 1 T w j 2 Obj^{\left(t\right)}=\sum_{i=1}^n\left[g_i f_t\left(\mathbf{x}_i\right)+\frac{1}{2}h_i f^2_t\left(\mathbf{x}_i\right)\right]+\gamma T+ \frac{1}{2}\lambda\sum_{j=1}^T w_j^2 Obj(t)=i=1∑n[gift(xi)+21hift2(xi)]+γT+21λj=1∑Twj2
4> 神来之笔(也是全PPT最难理解的地方)
最终得到这个公式需要知道两处设计非常精巧的内容:
- 关于树模型的定义
(4.1) f ( x ) = w q ( x ) f\left(\mathbf{x}\right)=w_{q\left(\mathbf{x}\right)} \tag{4.1} f(x)=wq(x)(4.1)其中, q : R m → { 1 , … , T } , w ∈ R T q:\mathbb{R}^m\to \{1,\dots,T\},w\in\mathbb{R}^T q:Rm→{1,…,T},w∈RT, T T T为决策树叶子节点数。
- 可以看到T代表叶子节点树,q代表函数将一个m维向量映射到叶子节点的标号 { 1 , … , T } \{1,\dots,T\} {1,…,T}之间,而 w w w是T维的向量每一维数字代表一个叶子节点的输出,所以模型直接定义了从x向量进入到划分输出均值的输出 w i w_{i} wi
- 关于
I
j
=
{
i
∣
q
(
x
i
)
=
j
}
I_j=\{i|q\left(\mathbf{x}_i\right)=j\}
Ij={i∣q(xi)=j}的应用
可以看到公式中 O b j ( t ) = ∑ i = 1 n [ g i f t ( x i ) + 1 2 h i f t 2 ( x i ) ] + γ T + 1 2 λ ∑ j = 1 T w j 2 Obj^{\left(t\right)}=\sum_{i=1}^n\left[g_i f_t\left(\mathbf{x}_i\right)+\frac{1}{2}h_i f^2_t\left(\mathbf{x}_i\right)\right]+\gamma T+ \frac{1}{2}\lambda\sum_{j=1}^T w_j^2 Obj(t)=i=1∑n[gift(xi)+21hift2(xi)]+γT+21λj=1∑Twj2
- n 代表样本数目, ∑ i = 1 n \sum_{i=1}^{n} ∑i=1n代表遍历每一个样本, f t ( x i ) f_{t}(x_{i}) ft(xi)的意思是说对于每一个 x i x_{i} xi得到他的决策树叶子节点的输出值【此刻是不是与上面1点相呼应,别急】,那么每一个叶子节点包含多个样本,也因此这个叶子节点对应的 f t ( x i ) f_{t}(x_{i}) ft(xi)值都相等
- T 代表叶子节点的个数,
∑
j
=
1
T
\sum_{j=1}^{T}
∑j=1T表示遍历每一个叶子节点,此时我们用叶子节点的标号
T
T
T 和
j
j
j去替换前面
n
n
n和
i
i
i 【也就是用一簇叶子节点样本替换一个一个样本】就得到了这一步(想想是不是,一定是!)
5> 最优w*和obj
至此一个标准的二次函数已经生成,会发现无论是这里的最优
w
∗
w^*
w∗和
o
b
j
obj
obj以及下面的CART树生长时的分裂属性和阈值的选择都是基于这个二次函数的基本性质
【高中公式极值点和极值公式】
6> 分裂属性和分裂值的选取
- GBDT算法分裂属性和分裂值选区中,有两层循环,外层循环是所有属性遍历,内存循环是把对应属性的范围进行分段遍历。
- XGboost对GBDT算法做了优化,对于一个分裂属性,可以算出当按照这个属性进行分裂时的左右子树的obj,那么如果不按照这个属性分裂,也会有一个不分裂的obj,这样我们就可以算出这个属性的obj增量-Gain,Gain如果是正的,并且值越大,就越容易选中切分,同时γ在这里实际上是一个临界值,它的值越大,表示我们对切分后obj下降幅度要求越严。这个值也是可以在xgboost中设定的。(也就是说还是归功于二次函数形式得到的最优值和最优的obj)
五、总结
从Boost
→
\to
→GBDT
→
\to
→XGboost,忽略所有的东西一条主线就是,GBDT的一阶
→
\to
→XGboost的二阶。
相较于GBDT而言,Xgboost带来的改进的地方确实是他的亮点
- 1.将损失函数从一阶推广到二阶可导的损失,GBDT使用的残差是泰勒展开式到一阶的结果,二XGboost是展开到二阶的结果。
- 2.加入了正则化项:控制模型的复杂度,模型复杂对于训练集误差很低,但是对于测试集的误差却很高,越容易发生过拟合
- 3.树生长的剪枝:分裂到最大深度,如果发现节点之后不再是正的损失,剔除。(见公式)
参考
1.Tianqi chen XGboost PPT
2.原始论文:XGBoost: A Scalable Tree Boosting System: https://arxiv.org/abs/1603.02754