日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 综合教程 >内容正文

综合教程

XGB 调参基本方法

發(fā)布時(shí)間:2024/8/5 综合教程 40 生活家
生活随笔 收集整理的這篇文章主要介紹了 XGB 调参基本方法 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

- xgboost 基本方法和默認(rèn)參數(shù)
- 實(shí)戰(zhàn)經(jīng)驗(yàn)中調(diào)參方法
- 基于實(shí)例具體分析

在訓(xùn)練過程中主要用到兩個(gè)方法:xgboost.train()和xgboost.cv().

xgboost.train(params,dtrain,num_boost_round=10,evals=(),obj=None,feval=None,maximize=False,early_stopping_rounds=None,
evals_result=None,verbose_eval=True,learning_rates=None,xgb_model=None)

  

params 這是一個(gè)字典,里面包含著訓(xùn)練中的參數(shù)關(guān)鍵字和對(duì)應(yīng)的值,形式是params = {‘booster’:’gbtree’,’eta’:0.1}
dtrain 訓(xùn)練的數(shù)據(jù)
evals 這是一個(gè)列表,用于對(duì)訓(xùn)練過程中進(jìn)行評(píng)估列表中的元素。形式是evals = [(dtrain,’train’),(dval,’val’)]或者是evals = [(dtrain,’train’)],對(duì)于第一種情況,它使得我們可以在訓(xùn)練過程中觀察驗(yàn)證集的效果。
obj,自定義目的函數(shù)
feval,自定義評(píng)估函數(shù)
early_stopping_rounds,早期停止次數(shù) ,假設(shè)為100,驗(yàn)證集的誤差迭代到一定程度在100次內(nèi)不能再繼續(xù)降低,就停止迭代。這要求evals 里至少有 一個(gè)元素,如果有多個(gè),按最后一個(gè)去執(zhí)行。返回的是最后的迭代次數(shù)(不是最好的)。如果early_stopping_rounds 存在,則模型會(huì)生成三個(gè)屬性,bst.best_score,bst.best_iteration,和bst.best_ntree_limit
evals_result 字典,存儲(chǔ)在watchlist 中的元素的評(píng)估結(jié)果。
verbose_eval (可以輸入布爾型或數(shù)值型),也要求evals 里至少有 一個(gè)元素。如果為True ,則對(duì)evals中元素的評(píng)估結(jié)果會(huì)輸出在結(jié)果中;如果輸入數(shù)字,假設(shè)為5,則每隔5個(gè)迭代輸出一次。

xgb_model ,在訓(xùn)練之前用于加載的xgb model。

scale_pos_weight [默認(rèn) 1]

在各類別樣本十分不平衡時(shí),把這個(gè)參數(shù)設(shè)定為一個(gè)正值,可以使算法更快收斂。

max_delta_step[默認(rèn)0]

這參數(shù)限制每棵樹權(quán)重改變的最大步長(zhǎng)。如果這個(gè)參數(shù)的值為0,那就意味著沒有約束。如果它被賦予了某個(gè)正值,那么它會(huì)讓這個(gè)算法更加保守。
通常,這個(gè)參數(shù)不需要設(shè)置。但是當(dāng)各類別的樣本十分不平衡時(shí),它對(duì)邏輯回歸是很有幫助的。
這個(gè)參數(shù)一般用不到,但是你可以挖掘出來它更多的用處。

params = {
            'booster':'gbtree',
            'objective':'binary:logistic',
            'eta':0.1,
            'max_depth':10,
            'subsample':1.0,
            'min_child_weight':5,
            'colsample_bytree':0.2,
            'scale_pos_weight':0.1,
            'eval_metric':'auc',
            'gamma':0.2,            
            'lambda':300
}

  

colsample_bytree 要依據(jù)特征個(gè)數(shù)來判斷
objective 目標(biāo)函數(shù)的選擇要根據(jù)問題確定,如果是回歸問題 ,一般是 reg:linear , reg:logistic , count:poisson 如果是分類問題,一般是binary:logistic ,rank:pairwise
參數(shù)初步定之后劃分20%為驗(yàn)證集,準(zhǔn)備一個(gè)watchlist 給train和validation set ,設(shè)置num_round 足夠大(比如100000),以至于你能發(fā)現(xiàn)每一個(gè)round 的驗(yàn)證集預(yù)測(cè)結(jié)果,如果在某一個(gè)round后 validation set 的預(yù)測(cè)誤差上升了,你就可以停止掉正在運(yùn)行的程序了。

watchlist = [(dtrain,'train'),(dval,'val')]
model = xgb.train(params,dtrain,num_boost_round=100000,evals = watchlist)

  

然后開始逐個(gè)調(diào)參了。

1、首先調(diào)整max_depth ,通常max_depth 這個(gè)參數(shù)與其他參數(shù)關(guān)系不大,初始值設(shè)置為10,找到一個(gè)最好的誤差值,然后就可以調(diào)整參數(shù)與這個(gè)誤差值進(jìn)行對(duì)比。比如調(diào)整到8,如果此時(shí)最好的誤差變高了,那么下次就調(diào)整到12;如果調(diào)整到12,誤差值比10 的低,那么下次可以嘗試調(diào)整到15.

2、在找到了最優(yōu)的max_depth之后,可以開始調(diào)整subsample,初始值設(shè)置為1,然后調(diào)整到0.8 如果誤差值變高,下次就調(diào)整到0.9,如果還是變高,就保持為1.0
3、接著開始調(diào)整min_child_weight , 方法與上面同理
4、再接著調(diào)整colsample_bytree
5、經(jīng)過上面的調(diào)整,已經(jīng)得到了一組參數(shù),這時(shí)調(diào)整eta 到0.05,然后讓程序運(yùn)行來得到一個(gè)最佳的num_round,(在 誤差值開始上升趨勢(shì)的時(shí)候?yàn)樽罴?)

另外:

很幸運(yùn)的是,Scikit-learn中提供了一個(gè)函數(shù)可以幫助我們更好地進(jìn)行調(diào)參:

sklearn.model_selection.GridSearchCV

常用參數(shù)解讀:

estimator:所使用的分類器,如果比賽中使用的是XGBoost的話,就是生成的model。比如: model = xgb.XGBRegressor(**other_params)
param_grid:值為字典或者列表,即需要最優(yōu)化的參數(shù)的取值。比如:cv_params = {‘n_estimators’: [550, 575, 600, 650, 675]}
scoring :準(zhǔn)確度評(píng)價(jià)標(biāo)準(zhǔn),默認(rèn)None,這時(shí)需要使用score函數(shù);或者如scoring=’roc_auc’,根據(jù)所選模型不同,評(píng)價(jià)準(zhǔn)則不同。字符串(函數(shù)名),或是可調(diào)用對(duì)象,需要其函數(shù)簽名形如:scorer(estimator, X, y);如果是None,則使用estimator的誤差估計(jì)函數(shù)。scoring參數(shù)選擇如下:

這次實(shí)戰(zhàn)我使用的是r2這個(gè)得分函數(shù),當(dāng)然大家也可以根據(jù)自己的實(shí)際需要來選擇。

調(diào)參剛開始的時(shí)候,一般要先初始化一些值:

learning_rate: 0.1
n_estimators: 500
max_depth: 5
min_child_weight: 1
subsample: 0.8
colsample_bytree:0.8
gamma: 0
reg_alpha: 0
reg_lambda: 1

你可以按照自己的實(shí)際情況來設(shè)置初始值,上面的也只是一些經(jīng)驗(yàn)之談吧。

調(diào)參的時(shí)候一般按照以下順序來進(jìn)行:

1、最佳迭代次數(shù):n_estimators

if __name__ == '__main__':
    trainFilePath = 'dataset/soccer/train.csv'
    testFilePath = 'dataset/soccer/test.csv'
    data = pd.read_csv(trainFilePath)
    X_train, y_train = featureSet(data)
    X_test = loadTestData(testFilePath)

    cv_params = {'n_estimators': [400, 500, 600, 700, 800]}
    other_params = {'learning_rate': 0.1, 'n_estimators': 500, 'max_depth': 5, 'min_child_weight': 1, 'seed': 0,
                    'subsample': 0.8, 'colsample_bytree': 0.8, 'gamma': 0, 'reg_alpha': 0, 'reg_lambda': 1}

    model = xgb.XGBRegressor(**other_params)
    optimized_GBM = GridSearchCV(estimator=model, param_grid=cv_params, scoring='r2', cv=5, verbose=1, n_jobs=4)
    optimized_GBM.fit(X_train, y_train)
    evalute_result = optimized_GBM.grid_scores_
    print('每輪迭代運(yùn)行結(jié)果:{0}'.format(evalute_result))
    print('參數(shù)的最佳取值:{0}'.format(optimized_GBM.best_params_))
    print('最佳模型得分:{0}'.format(optimized_GBM.best_score_))

  

寫到這里,需要提醒大家,在代碼中有一處很關(guān)鍵:

model = xgb.XGBRegressor(**other_params)中兩個(gè)*號(hào)千萬不能省略!可能很多人不注意,再加上網(wǎng)上很多教程估計(jì)是從別人那里直接拷貝,沒有運(yùn)行結(jié)果,所以直接就用了model = xgb.XGBRegressor(other_params)。悲劇的是,如果直接這樣運(yùn)行的話,會(huì)報(bào)如下錯(cuò)誤:

xgboost.core.XGBoostError: b"Invalid Parameter format for max_depth expect int but value...

  

不信,請(qǐng)看鏈接:xgboost issue

以上是血的教訓(xùn)啊,自己不運(yùn)行一遍代碼,永遠(yuǎn)不知道會(huì)出現(xiàn)什么Bug!

運(yùn)行后的結(jié)果為:

[Parallel(n_jobs=4)]: Done  25 out of  25 | elapsed:  1.5min finished
每輪迭代運(yùn)行結(jié)果:[mean: 0.94051, std: 0.01244, params: {'n_estimators': 400}, mean: 0.94057, std: 0.01244, params: {'n_estimators': 500}, mean: 0.94061, std: 0.01230, params: {'n_estimators': 600}, mean: 0.94060, std: 0.01223, params: {'n_estimators': 700}, mean: 0.94058, std: 0.01231, params: {'n_estimators': 800}]
參數(shù)的最佳取值:{'n_estimators': 600}
最佳模型得分:0.9406056804545407

  

由輸出結(jié)果可知最佳迭代次數(shù)為600次。但是,我們還不能認(rèn)為這是最終的結(jié)果,由于設(shè)置的間隔太大,所以,我又測(cè)試了一組參數(shù),這次粒度小一些:

cv_params = {'n_estimators': [550, 575, 600, 650, 675]}
other_params = {'learning_rate': 0.1, 'n_estimators': 600, 'max_depth': 5, 'min_child_weight': 1, 'seed': 0,
'subsample': 0.8, 'colsample_bytree': 0.8, 'gamma': 0, 'reg_alpha': 0, 'reg_lambda': 1}

運(yùn)行后的結(jié)果為:

每輪迭代運(yùn)行結(jié)果:[mean: 0.94065, std: 0.01237, params: {'n_estimators': 550}, mean: 0.94064, std: 0.01234, params: {'n_estimators': 575}, mean: 0.94061, std: 0.01230, params: {'n_estimators': 600}, mean: 0.94060, std: 0.01226, params: {'n_estimators': 650}, mean: 0.94060, std: 0.01224, params: {'n_estimators': 675}]
參數(shù)的最佳取值:{'n_estimators': 550}
最佳模型得分:0.9406545392685364

 

果不其然,最佳迭代次數(shù)變成了550。有人可能會(huì)問,那還要不要繼續(xù)縮小粒度測(cè)試下去呢?

這個(gè)我覺得可以看個(gè)人情況,如果你想要更高的精度,當(dāng)然是粒度越小,結(jié)果越準(zhǔn)確,大家可以自己慢慢去調(diào)試,我在這里就不一一去做了。

2、接下來要調(diào)試的參數(shù)是min_child_weight以及max_depth:

注意:每次調(diào)完一個(gè)參數(shù),要把 other_params對(duì)應(yīng)的參數(shù)更新為最優(yōu)值。

cv_params = {'max_depth': [3, 4, 5, 6, 7, 8, 9, 10], 'min_child_weight': [1, 2, 3, 4, 5, 6]}
other_params = {'learning_rate': 0.1, 'n_estimators': 550, 'max_depth': 5, 'min_child_weight': 1, 'seed': 0,
'subsample': 0.8, 'colsample_bytree': 0.8, 'gamma': 0, 'reg_alpha': 0, 'reg_lambda': 1}

運(yùn)行后的結(jié)果為:

[Parallel(n_jobs=4)]: Done 42 tasks | elapsed: 1.7min
[Parallel(n_jobs=4)]: Done 192 tasks | elapsed: 12.3min
[Parallel(n_jobs=4)]: Done 240 out of 240 | elapsed: 17.2min finished
每輪迭代運(yùn)行結(jié)果:[mean: 0.93967, std: 0.01334, params: {'min_child_weight': 1, 'max_depth': 3}, mean: 0.93826, std: 0.01202, params: {'min_child_weight': 2, 'max_depth': 3}, mean: 0.93739, std: 0.01265, params: {'min_child_weight': 3, 'max_depth': 3}, mean: 0.93827, std: 0.01285, params: {'min_child_weight': 4, 'max_depth': 3}, mean: 0.93680, std: 0.01219, params: {'min_child_weight': 5, 'max_depth': 3}, mean: 0.93640, std: 0.01231, params: {'min_child_weight': 6, 'max_depth': 3}, mean: 0.94277, std: 0.01395, params: {'min_child_weight': 1, 'max_depth': 4}, mean: 0.94261, std: 0.01173, params: {'min_child_weight': 2, 'max_depth': 4}, mean: 0.94276, std: 0.01329...]
參數(shù)的最佳取值:{'min_child_weight': 5, 'max_depth': 4}
最佳模型得分:0.94369522247392
由輸出結(jié)果可知參數(shù)的最佳取值:{'min_child_weight': 5, 'max_depth': 4}。(代碼輸出結(jié)果被我省略了一部分,因?yàn)榻Y(jié)果太長(zhǎng)了,以下也是如此)

  

3、接著我們就開始調(diào)試參數(shù):gamma:

cv_params = {'gamma': [0.1, 0.2, 0.3, 0.4, 0.5, 0.6]}
other_params = {'learning_rate': 0.1, 'n_estimators': 550, 'max_depth': 4, 'min_child_weight': 5, 'seed': 0,
'subsample': 0.8, 'colsample_bytree': 0.8, 'gamma': 0, 'reg_alpha': 0, 'reg_lambda': 1}

[Parallel(n_jobs=4)]: Done 30 out of 30 | elapsed: 1.5min finished
每輪迭代運(yùn)行結(jié)果:[mean: 0.94370, std: 0.01010, params: {'gamma': 0.1}, mean: 0.94370, std: 0.01010, params: {'gamma': 0.2}, mean: 0.94370, std: 0.01010, params: {'gamma': 0.3}, mean: 0.94370, std: 0.01010, params: {'gamma': 0.4}, mean: 0.94370, std: 0.01010, params: {'gamma': 0.5}, mean: 0.94370, std: 0.01010, params: {'gamma': 0.6}]
參數(shù)的最佳取值:{'gamma': 0.1}
最佳模型得分:0.94369522247392
由輸出結(jié)果可知參數(shù)的最佳取值:{'gamma': 0.1}。

4、接著是subsample以及colsample_bytree:

cv_params = {'subsample': [0.6, 0.7, 0.8, 0.9], 'colsample_bytree': [0.6, 0.7, 0.8, 0.9]}
other_params = {'learning_rate': 0.1, 'n_estimators': 550, 'max_depth': 4, 'min_child_weight': 5, 'seed': 0,
'subsample': 0.8, 'colsample_bytree': 0.8, 'gamma': 0.1, 'reg_alpha': 0, 'reg_lambda': 1}

運(yùn)行后的結(jié)果顯示參數(shù)的最佳取值:{'subsample': 0.7,'colsample_bytree': 0.7}

5、緊接著就是:reg_alpha以及reg_lambda:

cv_params = {'reg_alpha': [0.05, 0.1, 1, 2, 3], 'reg_lambda': [0.05, 0.1, 1, 2, 3]}
other_params = {'learning_rate': 0.1, 'n_estimators': 550, 'max_depth': 4, 'min_child_weight': 5, 'seed': 0,
'subsample': 0.7, 'colsample_bytree': 0.7, 'gamma': 0.1, 'reg_alpha': 0, 'reg_lambda': 1}

運(yùn)行后的結(jié)果為:

[Parallel(n_jobs=4)]: Done 42 tasks | elapsed: 2.0min
[Parallel(n_jobs=4)]: Done 125 out of 125 | elapsed: 5.6min finished
每輪迭代運(yùn)行結(jié)果:[mean: 0.94169, std: 0.00997, params: {'reg_alpha': 0.01, 'reg_lambda': 0.01}, mean: 0.94112, std: 0.01086, params: {'reg_alpha': 0.01, 'reg_lambda': 0.05}, mean: 0.94153, std: 0.01093, params: {'reg_alpha': 0.01, 'reg_lambda': 0.1}, mean: 0.94400, std: 0.01090, params: {'reg_alpha': 0.01, 'reg_lambda': 1}, mean: 0.93820, std: 0.01177, params: {'reg_alpha': 0.01, 'reg_lambda': 100}, mean: 0.94194, std: 0.00936, params: {'reg_alpha': 0.05, 'reg_lambda': 0.01}, mean: 0.94136, std: 0.01122, params: {'reg_alpha': 0.05, 'reg_lambda': 0.05}, mean: 0.94164, std: 0.01120...]
參數(shù)的最佳取值:{'reg_alpha': 1, 'reg_lambda': 1}
最佳模型得分:0.9441561344357595

由輸出結(jié)果可知參數(shù)的最佳取值:{'reg_alpha': 1, 'reg_lambda': 1}。

6、最后就是learning_rate,一般這時(shí)候要調(diào)小學(xué)習(xí)率來測(cè)試:

cv_params = {'learning_rate': [0.01, 0.05, 0.07, 0.1, 0.2]}
other_params = {'learning_rate': 0.1, 'n_estimators': 550, 'max_depth': 4, 'min_child_weight': 5, 'seed': 0,
'subsample': 0.7, 'colsample_bytree': 0.7, 'gamma': 0.1, 'reg_alpha': 1, 'reg_lambda': 1}

運(yùn)行后的結(jié)果為:

[Parallel(n_jobs=4)]: Done 25 out of 25 | elapsed: 1.1min finished
每輪迭代運(yùn)行結(jié)果:[mean: 0.93675, std: 0.01080, params: {'learning_rate': 0.01}, mean: 0.94229, std: 0.01138, params: {'learning_rate': 0.05}, mean: 0.94110, std: 0.01066, params: {'learning_rate': 0.07}, mean: 0.94416, std: 0.01037, params: {'learning_rate': 0.1}, mean: 0.93985, std: 0.01109, params: {'learning_rate': 0.2}]
參數(shù)的最佳取值:{'learning_rate': 0.1}
最佳模型得分:0.9441561344357595

由輸出結(jié)果可知參數(shù)的最佳取值:{'learning_rate': 0.1}。

我們可以很清楚地看到,隨著參數(shù)的調(diào)優(yōu),最佳模型得分是不斷提高的,這也從另一方面驗(yàn)證了調(diào)優(yōu)確實(shí)是起到了一定的作用。不過,我們也可以注意到,其實(shí)最佳分?jǐn)?shù)并沒有提升太多。提醒一點(diǎn),這個(gè)分?jǐn)?shù)是根據(jù)前面設(shè)置的得分函數(shù)算出來的,即:

optimized_GBM = GridSearchCV(estimator=model, param_grid=cv_params, scoring='r2', cv=5, verbose=1, n_jobs=4)
1
中的scoring='r2'。在實(shí)際情境中,我們可能需要利用各種不同的得分函數(shù)來評(píng)判模型的好壞。

最后,我們把得到的最佳參數(shù)組合扔到模型里訓(xùn)練,就可以得到預(yù)測(cè)的結(jié)果了:

def trainandTest(X_train, y_train, X_test):
    # XGBoost訓(xùn)練過程,下面的參數(shù)就是剛才調(diào)試出來的最佳參數(shù)組合
    model = xgb.XGBRegressor(learning_rate=0.1, n_estimators=550, max_depth=4, min_child_weight=5, seed=0,
                             subsample=0.7, colsample_bytree=0.7, gamma=0.1, reg_alpha=1, reg_lambda=1)
    model.fit(X_train, y_train)

    # 對(duì)測(cè)試集進(jìn)行預(yù)測(cè)
    ans = model.predict(X_test)

    ans_len = len(ans)
    id_list = np.arange(10441, 17441)
    data_arr = []
    for row in range(0, ans_len):
        data_arr.append([int(id_list[row]), ans[row]])
    np_data = np.array(data_arr)

    # 寫入文件
    pd_data = pd.DataFrame(np_data, columns=['id', 'y'])
    # print(pd_data)
    pd_data.to_csv('submit.csv', index=None)

    # 顯示重要特征
    # plot_importance(model)
    # plt.show()

  

好了,調(diào)參的過程到這里就基本結(jié)束了。正如我在上面提到的一樣,其實(shí)調(diào)參對(duì)于模型準(zhǔn)確率的提高有一定的幫助,但這是有限的。

最重要的還是要通過數(shù)據(jù)清洗,特征選擇,特征融合,模型融合等手段來進(jìn)行改進(jìn)!

原文:https://blog.csdn.net/sinat_35512245/article/details/79700029

參考文獻(xiàn)

https://www.kaggle.com/c/bnp-paribas-cardif-claims-management/forums/t/19083/best-practices-for-parameter-tuning-on-models
https://github.com/dmlc/xgboost/tree/master/demo
http://xgboost.readthedocs.io/en/latest/python/python_api.html

總結(jié)

以上是生活随笔為你收集整理的XGB 调参基本方法的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。