XGBoost 學習過程

2021-08-19 18:42:19 字數 3519 閱讀 7185

最近開始入手學習python處理資料,在看**的時候發現了xgboost,並且作為第三方庫在pycharm中無法匯入,很是一籌莫展,那就從部落格上搜尋開始入手,首先了解這個庫到底是完成了什麼事情呢。。。

下面開始據此對xgboost的原理做簡單的介紹…

xgboost[1]是2023年2月誕生的專注於梯度提公升演算法的機器學習函式庫,此函式庫因其優良的學習效果以及高效的訓練速度而獲得廣泛的關注。僅在2023年,在kaggle[2]競賽中獲勝的29個演算法中,有17個使用了xgboost庫,而作為對比,近年大熱的深度神經網路方法,這一資料則是11個。在kddcup 2015 [3]競賽中,排名前十的隊伍全部使用了xgboost庫。

xgboost不僅學習效果很好,而且速度也很快,相比梯度提公升演算法在另乙個常用機器學習庫scikit-learn中的實現,xgboost的效能經常有十倍以上的提公升。

在今年的kdd會議上,xgboost的作者陳天奇將這一庫函式所涉及到的理論推導和加速方法整理為**發表出來[4],本文據此對其原理做簡單的介紹。儘管這是乙個機器學習方面的函式庫,但其中有大量通用的加速方法,也值得我們學習。

1. gbdt演算法原理

xgboost實現的是一種通用的tree boosting演算法,此演算法的乙個代表為梯度提公升決策樹(gradient boosting decision tree, gbdt),又名mart(multiple additive regression tree)。

gbdt的原理是,首先使用訓練集和樣本真值(即標準答案)訓練一棵樹,然後使用這棵樹**訓練集,得到每個樣本的**值,由於**值與真值存在偏差,所以二者相減可以得到「殘差」。接下來訓練第二棵樹,此時不再使用真值,而是使用殘差作為標準答案。兩棵樹訓練完成後,可以再次得到每個樣本的殘差,然後進一步訓練第三棵樹,以此類推。樹的總棵數可以人為指定,也可以監控某些指標(例如驗證集上的誤差)來停止訓練。

在**新樣本時,每棵樹都會有乙個輸出值,將這些輸出值相加,即得到樣本最終的**值。

使用兩棵樹來**乙個人是否喜歡電腦遊戲的示意圖如下,小男孩和老人的**值為兩棵樹**值的加和。

xgboost所做的改進

2.1. 損失函式從平方損失推廣到二階可導的損失

gbdt的核心在於後面的樹擬合的是前面**值的殘差,這樣可以一步步逼近真值。然而,之所以擬合殘差可以逼近到真值,是因為使用了平方損失作為損失函式,公式如下

如果換成是其他損失函式,使用殘差將不再能夠保證逼近真值。xgboost的方法是,將損失函式做泰勒展開到第二階,使用前兩階作為改進的殘差。可以證明,傳統gbdt使用的殘差是泰勒展開到一階的結果,因此,gbdt是xgboost的乙個特例。注意:此處省略了嚴格的推導,詳情請參閱陳天奇的**。

2.2. 加入了正則化項

正則化方法是數學中用來解決不適定問題的一種方法,後來被引入機器學習領域。通俗的講,正則化是為了限制模型的複雜度的。模型越複雜,就越有可能「記住」訓練資料,導致訓練誤差達到很低,而測試誤差卻很高,也就是發生了「過擬合」。在機器學習領域,正則化項大多以懲罰函式的形式存在於目標函式中,也就是在訓練時,不僅只顧最小化誤差,同時模型複雜度也不能太高。

在決策樹中,模型複雜度體現在樹的深度上。xgboost使用了一種替代指標,即葉子節點的個數。此外,與許多其他機器學習模型一樣,xgboost也加入了l2正則項,來平滑各葉子節點的**值。

2.3. 支援列抽樣

列抽樣是指,訓練每棵樹時,不是使用所有特徵,而是從中抽取一部分來訓練這棵樹。這種方法原本是用在隨機森林中的,經過試驗,使用在gbdt中同樣有助於效果的提公升。

3.為什麼xgboost效果這麼好

xgboost是boosting演算法中的一種,其他的還包括adaboost等。boosting方法是目前最好的機器學習方法之一,關於其優良的學習效果,已有理論解釋包括偏差-方差分解和margin理論,但都不完美。下面結合個人理解做一些通俗的討論。

機器學習就是模型對資料的擬合。對於一組資料,使用過於複雜的模型去擬合,往往會發生過擬合,這時就需要引入正則化項來限制模型複雜度,然而正則化項的選取、正則化係數的設定都是比較隨意的,也比較難做到最佳。而如果使用過於簡單的模型,由於模型能力有限,很難把握資料中蘊含的規律,導致效果不佳。

boosting演算法比較巧妙,首先使用簡單的模型去擬合資料,得到乙個比較一般的結果,然後不斷向模型中新增簡單模型(多數情況下為層數較淺決策樹),隨著樹的增多,整個boosting模型的複雜度逐漸變高,直到接近資料本身的複雜度,此時訓練達到最佳水平。

因此,boosting演算法要取得良好效果,要求每棵樹都足夠「弱」,使得每次增加的複雜度都不大,同時樹的總數目要足夠多。xgboost中,對每棵樹的葉子節點數做了懲罰,從而限制了葉子節點的增長,使得每棵樹都是「弱」的,同時還引入了學習速率,進一步降低了每棵樹的影響。這樣做的代價是,數的總數目會多一些,但從其取得的效果上看,這樣做是值得的。

4. 為什麼xgboost執行這麼快

4.1. 連續型特徵的處理

決策樹在訓練時需要進行分叉,對於連續型特徵,列舉所有可能分叉點將會十分耗時。一種近似方法是只列舉若干個分位點,例如將所有樣本根據此特徵進行排序,然後均分10份,兩份之間斷開的數值即為分位點,列舉所有9個分位點後,使用降低損失最多的那個作為分叉點。

4.2. 利用資料稀疏性

資料稀疏有三個原因:缺失資料;某些特徵本身就含有大量的0;對離散特徵做了one-hot處理。無論是哪種,都會導致樣本中出現大量的0。通常,利用稀疏性可以提高運算效率。xgboost的方法是,每次分叉時,都指定一條預設分支,如果樣本的這個特徵為0,就走這個預設分支。這樣,訓練時不必考慮這些0元素,大大提高了運算速度。陳天奇的實驗表明,此方法在稀疏資料上可以提高50倍。

4.3. 資料的預排序和分塊儲存

分叉的時候為了判斷分叉點,需要對每個特徵進行排序。這個步驟是要重複多次的,因此xgboost在訓練之前預先對資料進行每一列做了排序,並按列儲存到記憶體中。在分布式環境下,可以進行分塊儲存。

4.4. 減少讀寫相關,提高cache命中率

由於預排序的資料是按列儲存的,但訓練時並不總是按列讀取和寫回,在需要按行讀寫的時候,將需要的行預先收集到一塊連續記憶體上,再進行計算。這樣由於是連續記憶體位址,可以提高cache命中率,從而提高了運算速度。

4.5. 資料量大時,提高硬碟吞吐率

當資料量很大,不能裝入記憶體時,需要將一部分資料放在硬碟裡。然而硬碟讀寫速度慢,會嚴重影響計算效率。xgboost使用了兩種方法提高吞吐率,乙個是對儲存的內容進行壓縮,讀取時再進行解壓,這相當於在讀取代價和解壓代價之間做了乙個權衡。另乙個方法是做資料分片,即在多塊硬碟上儲存資料,然後同時讀寫,從而提高讀寫速度。

5. 結語

xgboost綜合了前人關於梯度提公升演算法的眾多任務作,並在工程實現上做了大量優化,是目前最成功的機器學習演算法之一。目前,xgboost已被工業界廣泛使用,而gbdt及其改進演算法也幾乎成為了資料探勘面試的必考題目。本文只是對其進行了走馬觀花式的梳理,對於它更深入的數學原理和優化細節,還請參看陳天奇在kdd』16上的原始**[4]。

參考文獻

[1]

[2]

[3]

[4] chen t, guestrin c. xgboost: a scalable tree boosting system[c]. knowledge discovery and data mining, 2016.

機器學習 xgboost演算法過程推導

xgboost是boosting演算法的其中一種,該演算法思想就是不斷地新增樹,不斷地進行特徵 來生長一棵樹,每次新增乙個樹,其實是學習乙個新函式,去擬合上次 的殘差。具體的目標函式如下 主要就是找到ft來優化這一目標函式,通過乙個簡單的例子來形象的理解該目標函式。例如是小明真實有100個糖果,現在...

機器學習 xgboost

xgb中引數分為三類 1.通用引數 2.整合引數 3.任務引數 1 隨機森林在ligthgbm 有很多整合演算法 中有,裡面更全。2 xgboost 裡面有gdbt是樹的串型疊加的各種包,梯度增強的方法 裡面沒有隨機森林包。xgboost是乙個支援多種資料格式的庫。libsvm資料儲存格式,xgbo...

xgboost學習總結

特徵處理 缺失值處理 啞變數處理 附 需要處理啞變數的演算法有,knn glmnet svm xgboost 不需處理為啞變數的演算法有,logistic regression raprt gbm randomforest 一 模型引數 在訓練過程中主要用到兩個方法 xgboost.train 和x...