Xgboost理解


一、xgboost模型函數形式

  xgboost也是GBDT的一種,只不過GBDT在函數空間進行搜索最優F的時候,采用的是梯度下降法也就是一階泰勒展開;而xgboost采用的是二階泰勒展開也就是牛頓法,去每次逼近最優的F,泰勒展開越多與原函數形狀越接近,比如在x0處進行展開,其展開越多,x0附近與原函數值越接近,且這個附近的區域越大。另外一個xgboost加入了正則化項,有效防止過擬合。

  xgboost與GBDT都是采用的cart樹中的回歸樹來解決所有問題,回歸樹的預測輸出是實數分數,可以用於回歸、分類、排序等任務中。對於回歸問題,可以直接作為目標值,對於分類問題,需要映射成概率,比如采用邏輯回歸的sigmoid函數。

additive表示附加的,所謂additive training,就是每次add一顆樹進行學習,直到損失最小。

誤差函數盡量去擬合訓練數據,正則化項則鼓勵更加簡單的模型。因為當模型簡單之后,有限數據擬合出來結果的隨機性比較小,不容易過擬合,使得最后模型的預測更加穩定。

 

二、目標函數

1)回顧傳統參數空間的目標函數

誤差函數可以是square loss,logloss等,正則項可以是L1正則,L2正則等。正則項如果從Bayes角度來看,相當於對模型參數引入先驗分布:

L1正則,模型參數服從拉普拉斯分布,對參數加了分布約束,大部分取值為0。

L2正則,模型參數服從高斯分布,對參數加了分布約束,大部分絕對值很小。

2)xgboost在函數空間搜索的目標函數

函數空間的目標函數是多棵樹一起構建的目標損失函數,求解多棵樹一起的整體最優解。

 第一部分屬於誤差項,訓練模型的精度;第二部分正則項對每一棵回歸樹的復雜度進行了懲罰,使得學習出來的模型不容易過擬合。

 哪些指標可以衡量樹的復雜度呢?

樹的深度,內部節點個數,葉子節點個數,葉子節點分數等。

xgboost采用葉子節點個數T和葉子節點分數w(其實就是預測值)對樹的復雜度進行約束:

對葉子節點個數進行懲罰,相當於進行了剪枝。

 

三、泰勒展開

基本形式:

一階與二階泰勒展開:

1)一階泰勒展開(梯度下降法)

在機器學習任務中,需要最小化損失函數L(θ) ,其中θ 是要求解的模型參數。梯度下降法常用來求解這種無約束最優化問題,它是一種迭代方法:選取初值 θ0,不斷迭代,更新θ的值,進行損失函數的極小化。

從上面可知,當△θ=-αLt-1)時候,θ的更新就跟我們之前理解的梯度下降方法是一摸一樣。將△θ帶入損失函數即可知,這個時候L(θt)是肯定比L(θt-1)變小的。

所以,從梯度下降法角度理解,就是函數值沿着梯度的負方向進行減少;從泰勒展開角度理解,就是函數在θt-1處進行一階展開,並根據展開公式找到了比L(θt-1)更小的近似於L(θt)的值,因為泰勒展開本身就是用多項式形式近似表達函數的原形式。

2)二階泰勒展開(牛頓法)

此時如何進行優化,尋找更小的L(θt)?

 這時候利用泰勒二階展開求解最優的△θ,使得L(θt)更小,泰勒二階比一階肯定更接近原函數的值,所求得的△θ也使得L(θt)下降的更快,這就是牛頓法的優勢。

 

四、xgboost目標函數進行泰勒展開

xgboost在第t次迭代后,模型的預測等於前t-1次的模型預測加上第t棵樹的預測:

 

由於模型已經進行了t-1次迭代,也就是已經學習了t-1棵樹,此時只要學習尋找最優的第t棵樹函數ft即可,所以目標函數如下:

其中yiyi(t-1)都屬於已知的,可以理解為常數。

將目標函數在yi(t-1)處進行泰勒二次展開,因為我們一步步尋找的是最優的函數yi(t)使得L最小,就是上面所說的在函數空間進行的搜索,所以在yi(t-1)處進行泰勒二次展開尋找並學習下一顆樹ft,這里的ft其實就相當於上文第三部門牛頓法中的△θ,不停的尋找ft,最后將這些樹加起來就成了最優的yt,上文中也是不停的尋找△θ,最后θ*0+Σ△θ,一樣的道理。無非一個是在參數空間進行搜索,一個是在函數空間進行搜索。二次展開如下:

其中gihi分布如下:

                                

將常數項去掉,並把樹的結構形式帶入得到如下:

其實這個時候已經簡潔地變成對t棵樹的學習優化問題了,以葉子節點形式表示上述目標函數如下,其中Ij={i|q(xi)=j}表示j葉子節點上的樣本集合。

 為了使目標函數最小,可以令其導數為0,解得每個葉節點的最優預測分數為:

帶入目標函數,得到最小損失為:

五、如何進行分裂?

 1)如何評測節點分裂的優劣?

  ID3采用信息增益來評測,C4.5采用信息增益率、CART樹采用基尼系數和平方損失來評測,xgboost采用如下的打分評測:

其實就是上面的最小損失值的公式,如果分裂后能讓損失變得更小,就值得去分裂,所以分裂前后增益定義為:

這個Gain就是分裂前的損失-分裂后的損失,差值越大,代表分裂后的損失越小,所以當對一個節點進行分裂時,計算所有候選(feature,value)對應的gain,選區gain最大的進行分裂。

2)尋找分裂節點

1、精確算法-暴力窮舉搜索法

      遍歷所有特征的所有可能的分割點,計算gain值,選取gain值最大的(feature,value)去分割。該方式優點是精度高,缺點是計算量太大。

2、近似算法-分位點分割

      對於某一個特征,按照百分比確定候選分裂點,通過遍歷所有特征的所有候選分裂點來找到最佳分裂點,減少了計算復雜度。

  原論文指出兩種近似算法:一種是全局算法,即在初始化tree的時候划分好候選節點,並且在樹的每一層都使用這些候選節點;另一種是局部算法,即每一次划分的時候都重新計算候選節點。這兩者各有利弊,全局算法不需要多次計算候選節點,但需要一次獲取較多的候選節點供后續樹生長使用,而局部算法一次獲取的候選節點較少,可以在分支過程中不斷改善,即適用於生長更深的樹,兩者在effect和accuracy做trade off。
 

3.weighted quantile sketch(按權重的分位點算法)

該方法將樣本對應的殘差二階導h作為划分依據,假設每一個分位點區間的h之和占總h的比率為rk(z),則兩個相鄰區間的rk之差小於一個固定值,如下所示:

從上圖可知ε是一個小數,其實也就是將權重約分為了1/ε個分位點。

舉例如下:
第一行為一列特征對應的特征值,第二行為該特征值對應的樣本xi的二階導數值hi。
我的理解在一個個特征列上尋找分位點的時候,首先按照該列的特征值進行排序如上圖從小到大,然后再按權重hi計算rk,以上圖為例子計算如下:
rk(1)=0
rk(3)=(0.1+0.1)/(1.8)=1/9
rk(4)=(0.1+0.1+0.1)/(1.8)=1/6
rk(5)=0.4/1.8=2/9
rk(12)=0.5/1.8=5/18
rk(45)=0.6/1.8=1/3
rk(50)=1.0/1.8=5/9
rk(99)=1.2/1.8=2/3
所以如果取三分位點的時候,就是按rk=1/3,2/3的位置作為候選分裂點(即45,99兩個點)進行分裂增益計算,這樣大大減少了計算量。
之所以按二階導數h作為分位點划分,是因為我們要均分的是loss,而不是樣本的數量,而每個樣本對loss的貢獻可能是不一樣的,按樣本均分會導致loss分布不均勻,取到的分位點會有偏差,而h是對loss貢獻非常大的權重量,所以按h選取合適的分位點。
 
六、為什么要用泰勒二階展開?
1)可以很方便地自定義損失函數,只要這個損失函數可以求一階和二階 ,實現形式上的"統一"。
2)二階展開精度上更接近原函數,既有一階導數,也有二階導數,相當於既有速度信息,還有加速度信息,因此收斂更快。
 
七、其它
1)缺失值或者稀疏數據自動處理
    原論文中缺失值的處理與稀疏數據(大量為0的數據)的處理看作一樣。在尋找split point的時候,不會對該特征為missing的樣本進行遍歷統計,只對該列特征值為non-missing的樣本上對應的特征值進行遍歷,通過這個技巧來減少了為稀疏離散特征尋找split point的時間開銷。在邏輯實現上,為了保證完備性,會分別處理將missing該特征值的樣本分配到左葉子結點和右葉子結點的兩種情形,計算增益后選擇增益大的方向進行分裂即可。可以為缺失值或者指定的值指定分支的默認方向,這能大大提升算法的效率。如果在訓練中沒有缺失值而在預測中出現缺失,那么會自動將缺失值的划分方向放到右子樹。
 
2)特征預排序,存儲樣本索引。
    這樣加速了split finding的過程,只需要在建樹前排序一次,后面節點分裂時候,直接根據樣本能索引得到其樣本對應的梯度信息。
3)如何解決二分類問題輸出的概率值呢?
得到樹模型后,輸入一個原始數據,經過T個樹打分,殘差相加,得到的數值經過logictic function映射,然后就得到概率值了。
多分類問題,就采用softmax函數即可。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM