python 机器学习案例系列教程——LightGBM 算法
如果你觉得这篇⽂章看起来稍微还有些吃⼒,或者想要系统地学习⼈⼯智能,那么推荐你去看床长⼈⼯智能教程。⾮常棒的⼤神之作,教程不仅通俗易懂,⽽且很风趣幽默。点击可以查看教程。
xgboost 缺点
其缺点,或者说不⾜之处:
每轮迭代时,都需要遍历整个训练数据多次。如果把整个训练数据装进内存则会限制训练数据的⼤⼩;如果不装进内存,反复地读写训练数据⼜会消耗⾮常⼤的时间。
预排序⽅法(pre-sorted):⾸先,空间消耗⼤。这样的算法需要保存数据的特征值,还保存了特征排序的结果(例如排序后的索引,为了后续快速的计算分割点),这⾥需要消耗训练数据两倍的内存。其次时间上也有较⼤的开销,在遍历每⼀个分割点的时候,都需要进⾏分裂增益的计算,消耗的代价⼤。
对cache优化不友好。在预排序后,特征对梯度的访问是⼀种随机访问,并且不同的特征访问的顺序不⼀样,⽆法对cache进⾏优化。同时,在每⼀层长树的时候,需要随机访问⼀个⾏索引到叶⼦索引的数组,并且不同特征访问的顺序也不⼀样,也会造成较⼤的cache miss。
lightGBM 特点
以上与其说是xgboost的不⾜,倒不如说是lightGBM作者们构建新算法时着重瞄准的点。解决了什么问题,那么原来模型没解决就成了原模型的缺点。
安装
gitup⽹址:
中⽂教程
lightGBM 简介
xgboost的出现,让数据民⼯们告别了传统的机器学习算法们:RF、GBM、SVM、LASSO……..。现在微软推出了⼀个新的boosting框架,想要挑战xgboost的江湖地位。
顾名思义,lightGBM包含两个关键点:light即轻量级,GBM 梯度提升机。LightGBM 是⼀个梯度 boosting 框架,使⽤基于学习算法的决策树。它可以说是分布式的,⾼效的,有以下优势:更快的训练效率低内存使⽤更⾼的准确率⽀持并⾏化学习
可处理⼤规模数据pip install  lightgbm
1
概括来说,lightGBM主要有以下特点:
基于Histogram的决策树算法
带深度限制的Leaf-wise的叶⼦⽣长策略
直⽅图做差加速
直接⽀持类别特征(Categorical Feature)
Cache命中率优化
基于直⽅图的稀疏特征优化
多线程优化
前2个特点使我们尤为关注的。
Histogram算法
直⽅图算法的基本思想:先把连续的浮点特征值离散化成k个整数,同时构造⼀个宽度为k的直⽅图。遍
历数据时,根据离散化后的值作为索引在直⽅图中累积统计量,当遍历⼀次数据后,直⽅图累积了需要的统计量,然后根据直⽅图的离散值,遍历寻最优的分割点。
带深度限制的Leaf-wise的叶⼦⽣长策略
Level-wise过⼀次数据可以同时分裂同⼀层的叶⼦,容易进⾏多线程优化,也好控制模型复杂度,不容易过拟合。但实际上Level-wise是⼀种低效算法,因为它不加区分的对待同⼀层的叶⼦,带来了很多没必要的开销,因为实际上很多叶⼦的分裂增益较低,没必要进⾏搜索和分裂。
Leaf-wise则是⼀种更为⾼效的策略:每次从当前所有叶⼦中,到分裂增益最⼤的⼀个叶⼦,然后分裂,如此循环。因此同Level-wise相⽐,在分裂次数相同的情况下,Leaf-wise可以降低更多的误差,得到更好的精度。
Leaf-wise的缺点:可能会长出⽐较深的决策树,产⽣过拟合。因此LightGBM在Leaf-wise之上增加了⼀个最⼤深度限制,在保证⾼效率的同时防⽌过拟合。
xgboost和lightgbm
决策树算法
XGBoost使⽤的是pre-sorted算法,能够更精确的到数据分隔点;
⾸先,对所有特征按数值进⾏预排序。
其次,在每次的样本分割时,⽤O(# data)的代价到每个特征的最优分割点。
最后,到最后的特征以及分割点,将数据分裂成左右两个⼦节点。
优缺点:
这种pre-sorting算法能够准确到分裂点,但是在空间和时间上有很⼤的开销。
i. 由于需要对特征进⾏预排序并且需要保存排序后的索引值(为了后续快速的计算分裂点),因此内存需要训练数据的两倍。
ii. 在遍历每⼀个分割点的时候,都需要进⾏分裂增益的计算,消耗的代价⼤。
LightGBM使⽤的是histogram算法,占⽤的内存更低,数据分隔的复杂度更低。
其思想是将连续的浮点特征离散成k个离散值,并构造宽度为k的Histogram。然后遍历训练数据,统计每个离散值在直⽅图中的累计统计量。在进⾏特征选择时,只需要根据直⽅图的离散值,遍历寻最优的分割点。
Histogram 算法的优缺点:
Histogram算法并不是完美的。由于特征被离散化后,到的并不是很精确的分割点,所以会对结果产⽣影响。但在实际的数据集上表明,离散化的分裂点对最终的精度影响并不⼤,甚⾄会好⼀些。原因在于decision tree本⾝就是⼀个弱学习器,采⽤Histogram算法会起到正则化的效果,有效地防⽌模型的过拟合。
时间上的开销由原来的O(#data * #features)降到O(k * #features)。由于离散化,#bin远⼩于#data,因此时间上有很⼤的提升。
Histogram算法还可以进⼀步加速。⼀个叶⼦节点的Histogram可以直接由⽗节点的Histogram和兄弟节点的Histogram做差得到。
⼀般情况下,构造Histogram需要遍历该叶⼦上的所有数据,通过该⽅法,只需要遍历Histogram的k个捅。速度提升了⼀倍。
决策树⽣长策略
XGBoost采⽤的是按层⽣长level(depth)-wise⽣长策略,如Figure 1所⽰,能够同时分裂同⼀层的叶⼦,从⽽进⾏多线程优化,不容易过拟合;但不加区分的对待同⼀层的叶⼦,带来了很多没必要的开销。
因为实际上很多叶⼦的分裂增益较低,没必要进⾏搜索和分裂。
LightGBM采⽤leaf-wise⽣长策略,如Figure 2所⽰,每次从当前所有叶⼦中到分裂增益最⼤(⼀般也是数据量最⼤)的⼀个叶⼦,然后分裂,如此循环。因此同Level-wise相⽐,在分裂次数相同的情况下,Leaf-wise可以降低更多的误差,得到更好的精度。Leaf-wise的缺点是可能会长出⽐较深的决策树,产⽣过拟合。因此LightGBM在Leaf-wise之上增加了⼀个最⼤深度的限制,在保证⾼效率的同时防⽌过拟合。
⽹络通信优化
XGBoost由于采⽤pre-sorted算法,通信代价⾮常⼤,所以在并⾏的时候也是采⽤histogram算法;LightGBM采⽤的histogram算法通信代价⼩,通过使⽤集合通信算法,能够实现并⾏计算的线性加速。
LightGBM⽀持类别特征
实际上⼤多数机器学习⼯具都⽆法直接⽀持类别特征,⼀般需要把类别特征,转化one-hotting特征,降低了空间和时间的效率。⽽类别特征的使⽤是在实践中很常⽤的。基于这个考虑,LightGBM优化了对类别特征的⽀持,可以直接输⼊类别特征,不需要额外的0/1展开。并在决策树算法上增加了类别特征的决策规则。
lightGBM调参
所有的参数含义,参考:
调参过程:
(1)num_leaves
LightGBM使⽤的是leaf-wise的算法,因此在调节树的复杂程度时,使⽤的是num_leaves⽽不是max_depth。
⼤致换算关系:num_leaves = 2^(max_depth)
(2)样本分布⾮平衡数据集:可以param[‘is_unbalance’]=’true’
(3)Bagging参数:bagging_fraction+bagging_freq(必须同时设置)、feature_fraction
(4)min_data_in_leaf、min_sum_hessian_in_leaf
sklearn 接⼝形式的LightGBM ⽰例
这⾥主要以sklearn的使⽤形式来使⽤lightgbm算法,包含建模,训练,预测,⽹格参数优化。原⽣形式使⽤lightgbm
python是做什么的通俗易懂的import  lightgbm as  lgb import  pandas as  pd from  ics import  mean_squared_error from  del_selection import  GridSearchCV from
1
2
3
4
5
6
7
8# coding: utf-8# pylint: disable = invalid-name, C0111import  json import  lightgbm as  lgb import  pandas as  pd from  ics import  mean_squared_erro
1
2
3
4
5
6
7
8