推荐系统排序笔记1:GBDT、XGBoost
推荐系统排序笔记1:GBDT、XGBoost
推荐系统排序算法是机器学习领域的重要研究方向之一,其中GBDT和XGBoost是两种常用的排序算法。本文将详细介绍Boosting、GBDT和XGBoost的相关知识,帮助读者更好地理解这些算法的原理和应用。
1. BOOST模型
提升方法(Boosting),是一种可以用来减小监督式学习中偏差的机器学习算法。它是通过训练多个弱分类器,最后加权组合成一个强分类器。弱分类器一般是指一个分类器它的分类结果仅仅比随机分类好一点点。
boosting的算法过程如下:
- 对于训练集中的每个样本建立权值$w_i$,表示对每个样本的关注度。当某个样本被误分类的概率很高时,需要加大对该样本的权值。
- 进行迭代的过程中,每一步迭代都是一个弱分类器。我们需要用某种策略将其组合,作为最终模型。(例如AdaBoost给每个弱分类器一个权值,将其线性组合最为最终分类器。误差越小的弱分类器,权值越大)
- Boosting系列算法最经典的包括AdaBoost算法和GBDT算法。 Boosting是一种递进的组合方式,每一个新的分类器都在前一个分类器的预测结果上改进,所以说boosting是减少bias而bagging是减少variance的模型组合方式。
2. GBDT算法
GBDT(Gradient Boosting Decision Tree),全名叫梯度提升决策树,是一种迭代的决策树算法,又叫 MART(Multiple Additive Regression Tree),它通过构造一组弱的学习器(树),并把多颗决策树的结果累加起来作为最终的预测输出。该算法将决策树与集成思想进行了有效的结合。
GBDT用于分类:无论是GBDT分类算法还是回归算法,弱学习器都是回归树,这是由残差本质决定的。
RF也是多棵树,但从效果上有实践证明不如GBDT。且GBDT前面的树,特征分裂主要体现对多数样本有区分度的特征;后面的树,主要体现的是经过前N颗树,残差仍然较大的少数样本。优先选用在整体上有区分度的特征,再选用针对少数样本有区分度的特征,思路更加合理,这应该也是用GBDT的原因。
3. XGBoost
Xgboost(Extreme Gradient Boosting)是由陈天奇等人开发的一种优化分布式梯度提升库的开源实现。它通过优化目标函数和正则化项来提高模型的泛化能力,并且在计算速度和精度上都表现出色。
优点:
- 支持多种类型的损失函数,包括自定义损失函数。
- 使用了列子采样和行子采样技术,有效防止过拟合。
- 支持分布式计算,能够处理大规模数据集。
缺点:
- 对于高维稀疏数据,Xgboost的效率可能不如LightGBM。
- 在某些情况下,可能需要手动调整参数以获得最佳性能。
3.1 XGBoost目标函数的推导
XGBoost在GBDT的基础上,增加了正则化项,
用GBDT的方式,表达XGboost可以得到,当前值是前面的树的结果加上当前的预测值。其损失可以展开表示。
接下来,三个步骤优化XGBoost目标函数。
- 第一步:二阶泰勒展开,去除常数项,优化损失函数项;
- 第二步:正则化项展开,去除常数项,优化正则化项;
- 第三步:合并一次项系数、二次项系数,得到最终目标函数。
对于该损失函数,可以采用泰勒二阶展开的方式进行展开。目的是分离常数项
- 二阶泰勒展开,去除常数项,优化损失函数项;
- 简化正则项
移除常数项的原因是,其不影响我们求极值。t是目前第t棵树,t-1棵树的结果都是已知的。 - 合并一次项系数、二次项系数
最后,合并一次项系数、二次项系数。
3.2 XGBoost目标函数解
已知目标函数了,那我们对其求极值,就能够得到损失函数最小的最优解。
3.3 XGBoost树训练
在实际训练XGBoost树中,最佳分裂点是一个关键问题。第一颗树是所有样本的均值。
- 一些补充
贪心算法
也就是计算$Gain=Obj_{上一个}-Obj_{当前}$,找出计算出的$Gain$最小的节点,选择并继续分裂,如果$Gain$大于0,说明$Obj_{当前}$损失变大了,那么可以及时止损,停止分裂。XGBoost全局与局部策略的加权分位
局部策略:每次重新计算分位点。好处:比较灵活,数可以根据当前节点和样本的情况,重新划分。避免全局策略进一步很难划分的情况。
效果:
- XGboost如何自动处理缺省值?
- 收缩率shrinkage
- 一些注意
XGboost也是构建了多颗决策树的,其目标值是Obj最小,公式中t是第t颗树,j是第j个叶子结点。 - 疑问1:XGBOOST中的一棵树是怎么分裂的?分裂条件是什么,又是什么情况下又去构建第二棵树呢
- 回答:
3.4 XGBoost的sklearn参数示例
# 创建 XGBoost 分类器实例
# n_estimators=100 表示使用 100 棵树进行提升,即迭代 100 次
# max_depth=3 限制每棵树的最大深度为 3,防止过拟合
# learning_rate=0.1 控制每棵树对最终结果的贡献程度,较小的值使模型更稳定但收敛慢
# objective='multi:softmax' 表示处理多分类问题,使用 softmax 函数输出概率
# num_class=3 明确类别数量为 3,因为鸢尾花数据集有 3 个类别
# eval_metric='merror' 用于在训练过程中监控多分类错误率
model = XGBClassifier(
n_estimators=100,
max_depth=3,
learning_rate=0.1,
objective='multi:softmax',
num_class=3,
eval_metric='merror'
)
3.5 XGBoost面经
1. 什么是 XGBoost?
XGBoost(eXtreme Gradient Boosting)是一个高效的机器学习算法,常用于分类和回归任务。XGBoost 对 GBDT 进行了一系列优化,比如损失函数进行了二阶泰勒展开、目标函数加入正则项、支持并行和默认缺失值处理等,在可扩展性和训练速度上有了巨大的提升。
算法原理、带正则化项的目标函数、基于决策树的目标函数
GBDT 和 XGBoost 的区别?
XGBoost 如何评价特征的重要性?
XGBoost 为什么可以并行训练?
XGBoost 为什么快
- 分块并行在建树的过程中,最耗时的一个步骤就是在每次寻找最佳分裂点是都需要对特征的值进行排序。而 XGBoost 在训练之前,根据特征对数据进行了排序,然后保存到块结构中,并在每个块结构中都采用了稀疏矩阵存储格式(Compressed Sparse Columns Format,CSC)进行存储,后面的训练过程中会重复地使用块结构,可以大大减小计算量。每一个块结构包括一个或多个已经排序好的特征;缺失特征值将不进行排序;每个特征会存储指向样本梯度统计值的索引,方便计算一阶导和二阶导数值;这种块结构存储的特征之间相互独立,方便计算机进行并行计算。在对节点进行分裂时需要选择增益最大的特征作为分裂,这时各个特征的增益计算可以同时进行,这也是 Xgboost 能够实现分布式或者多线程计算的原因。
- 候选分位点:每个特征采用常数个分位点作为候选分割点
- CPU 缓存命中优化块结构的设计可以减少节点分裂时的计算量,但特征值通过索引访问样本梯度统计值的设计会导致访问操作的内存空间不连续,这样会造成缓存命中率低,从而影响到算法的效率。为了解决缓存命中率低的问题,XGBoost 提出了缓存访问优化算法,为每个线程分配一个连续的缓存区,将需要的梯度信息存放在缓冲区中,这样就是实现了非连续空间到连续空间的转换,提高了算法效率。此外适当调整块大小,也可以有助于缓存优化。
- Block 处理优化:Block预先放入内存;Block按列进行解压缩;将 Block 划分到不同硬盘来提高吞吐
- XGBoost 算法的优缺点?
- XGBoost 中如果目标函数不可导怎么办?
参考:
- 精排-详解排序算法
- 机器学习算法之Boosting详解
- 深入理解CatBoost
- GBDT的原理、公式推导、Python实现、可视化和应用
- 【机器学习】深入剖析梯度提升决策树(GBDT)分类与回归
- 躺懂XGBoost,学不会来打我(doge)
- Xgboost,史上最强面试总结