天天看點

機器學習實戰 | LightGBM模組化應用詳解

機器學習實戰 | LightGBM模組化應用詳解

本篇詳細講解LightGBM的工程應用方法。LightGBM是微軟開發的boosting內建模型,和XGBoost一樣是對GBDT的優化和高效實作,但它很多方面比XGBoost有着更為優秀的表現。

機器學習實戰 | LightGBM模組化應用詳解

作者:韓信子@ShowMeAI

教程位址:https://www.showmeai.tech/tutorials/41

本文位址:https://www.showmeai.tech/article-detail/205

聲明:版權所有,轉載請聯系平台與作者并注明出處

收藏ShowMeAI檢視更多精彩内容

引言

LightGBM是微軟開發的boosting內建模型,和XGBoost一樣是對GBDT的優化和高效實作,原理有一些相似之處,但它很多方面比XGBoost有着更為優秀的表現。

本篇内容ShowMeAI展開給大家講解LightGBM的工程應用方法,對于LightGBM原理知識感興趣的同學,歡迎參考ShowMeAI的另外一篇文章 圖解機器學習 | LightGBM模型詳解。

1.LightGBM安裝

LightGBM作為常見的強大Python機器學習工具庫,安裝也比較簡單。

1.1 Python與IDE環境設定

python環境與IDE設定可以參考ShowMeAI文章 圖解python | 安裝與環境設定 進行設定。

機器學習實戰 | LightGBM模組化應用詳解

1.2 工具庫安裝

(1) Linux/Mac等系統

這些系統下的XGBoost安裝,大家隻要基于pip就可以輕松完成了,在指令行端輸入指令如下指令即可等待安裝完成。

pip install lightgbm
           

大家也可以選擇國内的pip源,以獲得更好的安裝速度:

pip install -i https://pypi.tuna.tsinghua.edu.cn/simple lightgbm
           

(2) Windows系統

對于windows系統而言,比較高效便捷的安裝方式是:在網址http://www.lfd.uci.edu/~gohlke/pythonlibs/ 中去下載下傳對應版本的的LightGBM安裝包,再通過如下指令安裝。

pip install lightgbm‑3.3.2‑cp310‑cp310‑win_amd64.whl

2.LightGBM參數手冊

在ShowMeAI的前一篇内容 XGBoost工具庫模組化應用詳解 中,我們講解到了Xgboost的三類參數通用參數,學習目标參數,Booster參數。而LightGBM可調參數更加豐富,包含核心參數,學習控制參數,IO參數,目标參數,度量參數,網絡參數,GPU參數,模型參數,這裡我常修改的便是核心參數,學習控制參數,度量參數等。下面我們對這些模型參數做展開講解,更多的細節可以參考LightGBM中文文檔。

2.1 參數介紹

(1) 核心參數

  • config

    或者

    config_file

    :一個字元串,給出了配置檔案的路徑。預設為空字元串。
  • task

    :一個字元串,給出了要執行的任務。可以為:
    • train

      或者

      training

      :表示是訓練任務。預設為

      train

    • predict

      或者

      prediction

      或者

      test

      :表示是預測任務。
    • convert_model

      :表示是模型轉換任務。将模型檔案轉換成if-else格式。
  • application

    或者

    objective

    或者

    app

    :一個字元串,表示問題類型。可以為:
    • regression

      regression_l2

      mean_squared_error

      mse

      l2_root

      root_mean_squred_error

      rmse

      :表示回歸任務,但是使用L2損失函數。預設為

      regression

    • regression_l1

      或者

      mae

      或者

      mean_absolute_error

      :表示回歸任務,但是使用L1損失函數。
    • huber

      :表示回歸任務,但是使用huber損失函數。
    • fair

      :表示回歸任務,但是使用fair損失函數。
    • poisson

      :表示Poisson回歸任務。
    • quantile

      :表示quantile回歸任務。
    • quantile_l2

      :表示quantile回歸任務,但是使用了L2損失函數。
    • mape

      或者

      mean_absolute_precentage_error

      :表示回歸任務,但是使用MAPE損失函數
    • gamma

      :表示gamma回歸任務。
    • tweedie

      :表示tweedie回歸任務。
    • binary

      :表示二分類任務,使用對數損失函數作為目标函數。
    • multiclass

      :表示多分類任務,使用softmax函數作為目标函數。必須設定

      num_class

      參數
    • multiclassova

      或者

      multiclass_ova

      或者

      ova

      或者

      ovr

      :表示多分類任務,使用

      one-vs-all

      的二分類目标函數。必須設定

      num_class

      參數。
    • xentropy

      或者

      cross_entropy

      :目标函數為交叉熵(同時具有可選擇的線性權重)。要求标簽是[0,1]之間的數值。
    • xentlambda

      或者

      cross_entropy_lambda

      :替代了參數化的

      cross_entropy

      。要求标簽是[0,1]之間的數值。
    • lambdarank

      :表示排序任務。在

      lambdarank

      任務中,标簽應該為整數類型,數值越大表示相關性越高。

      label_gain

      參數可以用于設定整數标簽的增益(權重)。
  • boosting

    或者

    boost

    或者

    boosting_type

    :一個字元串,給出了基學習器模型算法。可以為:
    • gbdt

      :表示傳統的梯度提升決策樹。預設值為

      gbdt

    • rf

      :表示随機森林。
    • dart

      :表示帶dropout的gbdt。
    • goss

      :表示Gradient-based One-Side Sampling 的gbdt。
  • data

    或者

    train

    或者

    train_data

    :一個字元串,給出了訓練資料所在的檔案的檔案名。預設為空字元串。LightGBM将使用它來訓練模型。
  • valid

    或者

    test

    或者

    valid_data

    或者

    test_data

    :一個字元串,表示驗證集所在的檔案的檔案名。預設為空字元串。LightGBM将輸出該資料集的度量。如果有多個驗證集,則用逗号分隔。
  • num_iterations

    或者

    num_iteration

    或者

    num_tree

    或者

    num_trees

    或者

    num_round

    或者

    num_rounds

    或者

    num_boost_round

    一個整數,給出了

    boosting

    的疊代次數。預設為100。
    • 對于Python/R包,該參數是被忽略的。對于Python,使用

      train()/cv()

      的輸入參數

      num_boost_round

      來代替。
    • 在内部,LightGBM對于multiclass問題設定了

      num_class*num_iterations

      棵樹。
  • learning_rate

    或者

    shrinkage_rate

    :個浮點數,給出了學習率。預設為1。在dart中,它還會影響dropped trees的歸一化權重。
  • num_leaves

    或者

    num_leaf

    :一個整數,給出了一棵樹上的葉子數。預設為31。
  • tree_learner

    或者

    tree

    :一個字元串,給出了tree learner,主要用于并行學習。預設為

    serial

    。可以為:
    • serial

      :單台機器的tree learner
    • feature

      :特征并行的tree learner
    • data

      :資料并行的tree learner
    • voting

      :投票并行的tree learner
  • num_threads

    或者

    num_thread

    或者

    nthread

    :一個整數,給出了LightGBM的線程數。預設為

    OpenMP_default

    • 為了更快的速度,應該将它設定為真正的CPU核心數,而不是線程的數量(大多數CPU使用超線程來使每個CPU核心生成2個線程)。
    • 當資料集較小的時候,不要将它設定的過大。
    • 對于并行學習,不應該使用全部的CPU核心,因為這會使得網絡性能不佳。
  • device

    :一個字元串,指定計算裝置。預設為

    cpu

    。可以為

    gpu

    cpu

    • 建議使用較小的

      max_bin

      來獲得更快的計算速度。
    • 為了加快學習速度,GPU預設使用32位浮點數來求和。你可以設定

      gpu_use_dp=True

      來啟動64位浮點數,但是它會使得訓練速度降低。

(2) 學習控制參數

  • max_depth

    :一個整數,限制了樹模型的最大深度,預設值為-1。如果小于0,則表示沒有限制。
  • min_data_in_leaf

    或者

    min_data_per_leaf

    或者

    min_data

    或者

    min_child_samples

    :一個整數,表示一個葉子節點上包含的最少樣本數量。預設值為20。
  • min_sum_hessian_in_leaf

    或者

    min_sum_hessian_per_leaf

    或者

    min_sum_hessian

    或者

    min_hessian

    或者

    min_child_weight

    :一個浮點數,表示一個葉子節點上的最小hessian之和。(也就是葉節點樣本權重之和的最小值)預設為1e-3。
  • feature_fraction

    或者

    sub_feature

    或者

    colsample_bytree

    :一個浮點數,取值範圍為[0.0,1.0],預設值為0。如果小于1.0,則LightGBM會在每次疊代中随機選擇部分特征。如0.8表示:在每棵樹訓練之前選擇80%的特征來訓練。
  • feature_fraction_seed

    :一個整數,表示

    feature_fraction

    的随機數種子,預設為2。
  • bagging_fraction

    或者

    sub_row

    或者

    subsample

    :一個浮點數,取值範圍為[0.0,1.0],預設值為0。如果小于1.0,則LightGBM會在每次疊代中随機選擇部分樣本來訓練(非重複采樣)。如0.8表示:在每棵樹訓練之前選擇80%的樣本(非重複采樣)來訓練。
  • bagging_freq

    或者

    subsample_freq

    :一個整數,表示每

    bagging_freq

    次執行bagging。如果該參數為0,表示禁用bagging。
  • bagging_seed

    或者

    bagging_fraction_seed

    :一個整數,表示bagging的随機數種子,預設為3。
  • early_stopping_round

    或者

    early_stopping_rounds

    或者

    early_stopping

    :一個整數,預設為0。如果一個驗證集的度量在

    early_stopping_round

    循環中沒有提升,則停止訓練。如果為0則表示不開啟早停。
  • lambda_l1

    或者

    reg_alpha

    :一個浮點數,表示L1正則化系數。預設為0。
  • lambda_l2

    或者

    reg_lambda

    :一個浮點數,表示L2正則化系數。預設為0。
  • min_split_gain

    或者

    min_gain_to_split

    :一個浮點數,表示執行切分的最小增益,預設為0。
  • drop_rate

    :一個浮點數,取值範圍為[0.0,1.0],表示dropout的比例,預設為1。該參數僅在dart中使用。
  • skip_drop

    :一個浮點數,取值範圍為[0.0,1.0],表示跳過dropout的機率,預設為5。該參數僅在dart中使用。
  • max_drop

    :一個整數,表示一次疊代中删除樹的最大數量,預設為50。如果小于等于0,則表示沒有限制。該參數僅在dart中使用。
  • uniform_drop

    :一個布爾值,表示是否想要均勻的删除樹,預設值為False。該參數僅在dart中使用。
  • xgboost_dart_mode

    :一個布爾值,表示是否使用xgboost dart模式,預設值為False。該參數僅在dart中使用。
  • drop_seed

    :一個整數,表示dropout的随機數種子,預設值為4。該參數僅在dart中使用。
  • top_rate

    :一個浮點數,取值範圍為[0.0,1.0],表示在goss中,大梯度資料的保留比例,預設值為2。該參數僅在goss中使用。
  • other_rate

    :一個浮點數,取值範圍為[0.0,1.0],表示在goss中,小梯度資料的保留比例,預設值為1。該參數僅在goss中使用。
  • min_data_per_group

    :一個整數,表示每個分類組的最小資料量,預設值為100。用于排序任務
  • max_cat_threshold

    :一個整數,表示category特征的取值集合的最大大小。預設為32。
  • cat_smooth

    :一個浮點數,用于category特征的機率平滑。預設值為10。它可以降低噪聲在category特征中的影響,尤其是對于資料很少的類。
  • cat_l2

    :一個浮點數,用于category切分中的L2正則化系數。預設為10。
  • top_k

    或者

    topk

    :一個整數,用于投票并行中。預設為20。将它設定為更大的值可以獲得更精确的結果,但是會降低訓練速度。

(3) IO參數

  • max_bin

    :一個整數,表示最大的桶的數量。預設值為255。LightGBM會根據它來自動壓縮記憶體。如

    max_bin=255

    時,則LightGBM将使用uint8來表示特征的每一個值。
  • min_data_in_bin

    :一個整數,表示每個桶的最小樣本數。預設為3。該方法可以避免出現一個桶隻有一個樣本的情況。
  • data_random_seed

    :一個整數,表示并行學習資料分隔中的随機數種子。預設為1它不包括特征并行。
  • output_model

    或者

    model_output

    或者

    model_out

    :一個字元串,表示訓練中輸出的模型被儲存的檔案的檔案名。預設txt。
  • input_model

    或者

    model_input

    或者

    model_in

    :一個字元串,表示輸入模型的檔案的檔案名。預設空字元串。對于prediction任務,該模型将用于預測資料,對于train任務,訓練将從該模型繼續
  • output_result

    或者

    predict_result

    或者

    prediction_result

    :一個字元串,給出了prediction結果存放的檔案名。預設為txt。
  • pre_partition

    或者

    is_pre_partition

    :一個布爾值,訓示資料是否已經被劃分。預設值為False。如果為true,則不同的機器使用不同的partition來訓練。它用于并行學習(不包括特征并行)
  • is_sparse

    或者

    is_enable_sparse

    或者

    enable_sparse

    :一個布爾值,表示是否開啟稀疏優化,預設為True。如果為True則啟用稀疏優化。
  • two_round

    或者

    two_round_loading

    或者

    use_two_round_loading

    :一個布爾值,訓示是否啟動兩次加載。預設值為False,表示隻需要進行一次加載。預設情況下,LightGBM會将資料檔案映射到記憶體,然後從記憶體加載特征,這将提供更快的資料加載速度。但是當資料檔案很大時,記憶體可能會被耗盡。如果資料檔案太大,則将它設定為True
  • save_binary

    或者

    is_save_binary

    或者

    is_save_binary_file

    :一個布爾值,表示是否将資料集(包括驗證集)儲存到二進制檔案中。預設值為False。如果為True,則可以加快資料的加載速度。
  • verbosity

    或者

    verbose

    :一個整數,表示是否輸出中間資訊。預設值為1。如果小于0,則僅僅輸出critical資訊;如果等于0,則還會輸出error,warning資訊;如果大于0,則還會輸出info資訊。
  • header

    或者

    has_header

    :一個布爾值,表示輸入資料是否有頭部。預設為False。
  • label

    或者

    label_column

    :一個字元串,表示标簽列。預設為空字元串。你也可以指定一個整數,如label=0表示第0列是标簽列。你也可以為列名添加字首,如

    label=prefix:label_name

  • weight

    或者

    weight_column

    :一個字元串,表示樣本權重列。預設為空字元串。你也可以指定一個整數,如weight=0表示第0列是權重列。注意:它是剔除了标簽列之後的索引。假如标簽列為0,權重列為1,則這裡weight=0。你也可以為列名添加字首,如

    weight=prefix:weight_name

  • query

    或者

    query_column

    或者

    gourp

    或者

    group_column

    :一個字元串,query/groupID列。預設為空字元串。你也可以指定一個整數,如query=0表示第0列是query列。注意:它是剔除了标簽列之後的索引。假如标簽列為0,query列為1,則這裡query=0。你也可以為列名添加字首,如

    query=prefix:query_name

  • ignore_column

    或者

    ignore_feature

    或者

    blacklist

    :一個字元串,表示訓練中忽略的一些列,預設為空字元串。可以用數字做索引,如

    ignore_column=0,1,2

    表示第0,1,2列将被忽略。注意:它是剔除了标簽列之後的索引。
  • 你也可以為列名添加字首,如

    ignore_column=prefix:ign_name1,ign_name2

  • categorical_feature

    或者

    categorical_column

    或者

    cat_feature

    或者

    cat_column

    :一個字元串,指定category特征的列。預設為空字元串。可以用數字做索引,如

    categorical_feature=0,1,2

    表示第0,1,2列将作為category特征。注意:它是剔除了标簽列之後的索引。你也可以為列名添加字首,如

    categorical_feature=prefix:cat_name1,cat_name2

    在categorycal特征中,負的取值被視作缺失值。
  • predict_raw_score

    或者

    raw_score

    或者

    is_predict_raw_score

    :一個布爾值,表示是否預測原始得分。預設為False。如果為True則僅預測原始得分。該參數隻用于prediction任務。
  • predict_leaf_index

    或者

    leaf_index

    或者

    is_predict_leaf_index

    :一個布爾值,表示是否預測每個樣本在每棵樹上的葉節點編号。預設為False。在預測時,每個樣本都會被配置設定到每棵樹的某個葉子節點上。該參數就是要輸出這些葉子節點的編号。該參數隻用于prediction任務。
  • predict_contrib

    或者

    contrib

    或者

    is_predict_contrib

    :一個布爾值,表示是否輸出每個特征對于每個樣本的預測的貢獻。預設為False。輸出的結果形狀為[nsamples,nfeatures+1],之是以+1是考慮到bais的貢獻。所有的貢獻加起來就是該樣本的預測結果。該參數隻用于prediction任務。
  • bin_construct_sample_cnt

    或者

    subsample_for_bin

    :一個整數,表示用來建構直方圖的樣本的數量。預設為200000。如果資料非常稀疏,則可以設定為一個更大的值,如果設定更大的值,則會提供更好的訓練效果,但是會增加資料加載時間。
  • num_iteration_predict

    :一個整數,表示在預測中使用多少棵子樹。預設為-1。小于等于0表示使用模型的所有子樹。該參數隻用于prediction任務。
  • pred_early_stop

    :一個布爾值,表示是否使用早停來加速預測。預設為False。如果為True,則可能影響精度。
  • pred_early_stop_freq

    :一個整數,表示檢查早停的頻率。預設為10
  • pred_early_stop_margin

    :一個浮點數,表示早停的邊際門檻值。預設為0
  • use_missing

    :一個布爾值,表示是否使用缺失值功能。預設為True如果為False則禁用缺失值功能。
  • zero_as_missing

    :一個布爾值,表示是否将所有的零(包括在libsvm/sparse矩陣中未顯示的值)都視為缺失值。預設為False。如果為False,則将nan視作缺失值。如果為True,則

    np.nan

    和零都将視作缺失值。
  • init_score_file

    :一個字元串,表示訓練時的初始化分數檔案的路徑。預設為空字元串,表示train_data_file+”.init”(如果存在)
  • valid_init_score_file

    :一個字元串,表示驗證時的初始化分數檔案的路徑。預設為空字元串,表示valid_data_file+”.init”(如果存在)。如果有多個(對應于多個驗證集),則可以用逗号

    ,

    來分隔。

(4) 目标參數

  • sigmoid

    :一個浮點數,用sigmoid函數的參數,預設為0。它用于二分類任務和lambdarank任務。
  • alpha

    :一個浮點數,用于Huber損失函數和Quantileregression,預設值為0。它用于huber回歸任務和Quantile回歸任務。
  • fair_c

    :一個浮點數,用于Fair損失函數,預設值為0。它用于fair回歸任務。
  • gaussian_eta

    :一個浮點數,用于控制高斯函數的寬度,預設值為0。它用于regression_l1回歸任務和huber回歸任務。
  • posson_max_delta_step

    :一個浮點數,用于Poisson regression的參數,預設值為7。它用于poisson回歸任務。
  • scale_pos_weight

    :一個浮點數,用于調整正樣本的權重,預設值為0它用于二分類任務。
  • boost_from_average

    :一個布爾值,訓示是否将初始得分調整為平均值(它可以使得收斂速度更快)。預設為True。它用于回歸任務。
  • is_unbalance

    或者

    unbalanced_set

    :一個布爾值,訓示訓練資料是否均衡的。預設為True。它用于二分類任務。
  • max_position

    :一個整數,訓示将在這個NDCG位置優化。預設為20。它用于lambdarank任務。
  • label_gain

    :一個浮點數序列,給出了每個标簽的增益。預設值為0,1,3,7,15,….它用于lambdarank任務。
  • num_class

    或者

    num_classes

    :一個整數,訓示了多分類任務中的類别數量。預設為1它用于多分類任務。
  • reg_sqrt

    :一個布爾值,預設為False。如果為True,則拟合的結果為:\sqrt{label}。同時預測的結果被自動轉換為:{pred}^2。它用于回歸任務。

(5) 度量參數

  • metric

    :一個字元串,指定了度量的名額,預設為:對于回歸問題,使用l2;對于二分類問題,使用

    binary_logloss

    ;對于lambdarank問題,使用ndcg。如果有多個度量名額,則用逗号

    ,

    分隔。
    • l1

      或者

      mean_absolute_error

      或者

      mae

      或者

      regression_l1

      :表示絕對值損失。
    • l2

      或者

      mean_squared_error

      或者

      mse

      或者

      regression_l2

      或者

      regression

      :表示平方損失。
    • l2_root

      或者

      root_mean_squared_error

      或者

      rmse

      :表示開方損失。
    • quantile

      :表示Quantile回歸中的損失。
    • mape

      或者

      mean_absolute_percentage_error

      :表示MAPE損失。
    • huber

      :表示huber損失。
    • fair

      :表示fair損失。
    • poisson

      :表示poisson回歸的負對數似然。
    • gamma

      :表示gamma回歸的負對數似然。
    • gamma_deviance

      :表示gamma回歸的殘差的方差。
    • tweedie

      :表示Tweedie回歸的負對數似然。
    • ndcg

      :表示NDCG。
    • map

      或者

      mean_average_precision

      :表示平均的精度。
    • auc

      :表示AUC。
    • binary_logloss

      或者

      binary

      :表示二類分類中的對數損失函數。
    • binary_error

      :表示二類分類中的分類錯誤率。
    • multi_logloss

      或者

      multiclass

      或者

      softmax

      或者‘multiclassova

      或者

      multiclass_ova

      ,或者

      ova

      或者

      ovr`:表示多類分類中的對數損失函數。
    • multi_error

      :表示多分類中的分類錯誤率。
    • xentropy

      或者

      cross_entropy

      :表示交叉熵。
    • xentlambda

      或者

      cross_entropy_lambda

      :表示intensity權重的交叉熵。
    • kldiv

      或者

      kullback_leibler

      :表示KL散度。
  • metric_freq

    或者

    output_freq

    :一個正式,表示每隔多少次輸出一次度量結果。預設為1。
  • train_metric

    或者

    training_metric

    或者

    is_training_metric

    :一個布爾值,預設為False。如果為True,則在訓練時就輸出度量結果。
  • ndcg_at

    或者

    ndcg_eval_at

    或者

    eval_at

    :一個整數清單,指定了NDCG評估點的位置。預設為1、2、3、4、5。

2.2 參數影響與調參建議

以下為總結的核心參數對模型的影響,及與之對應的調參建議。

(1) 對樹生長控制

機器學習實戰 | LightGBM模組化應用詳解
  • num_leaves

    :葉節點的數目。它是控制樹模型複雜度的主要參數。
    • 如果是

      level-wise

      ,則該參數為\(2^{depth}\),其中depth為樹的深度。但是當葉子數量相同時,leaf-wise的樹要遠遠深過level-wise樹,非常容易導緻過拟合。是以應該讓num_leaves小于\(2^{depth}\)。在leaf-wise樹中,并不存在depth的概念。因為不存在一個從leaves到depth的合理映射。
  • min_data_in_leaf

    :每個葉節點的最少樣本數量。
    • 它是處理

      leaf-wise

      樹的過拟合的重要參數。将它設為較大的值,可以避免生成一個過深的樹。但是也可能導緻欠拟合。
  • max_depth

    :樹的最大深度。該參數可以顯式的限制樹的深度。

(2) 更快的訓練速度

機器學習實戰 | LightGBM模組化應用詳解
  • 通過設定

    bagging_fraction

    bagging_freq

    參數來使用bagging方法。
  • 通過設定

    feature_fraction

    參數來使用特征的子抽樣。
  • 使用較小的

    max_bin

  • 使用

    save_binary

    在未來的學習過程對資料加載進行加速。

(3) 更好的模型效果

機器學習實戰 | LightGBM模組化應用詳解
  • 使用較大的

    max_bin

    (學習速度可能變慢)。
  • 使用較小的

    learning_rate

    和較大的

    num_iterations

  • 使用較大的

    num_leaves

    (可能導緻過拟合)。
  • 使用更大的訓練資料。
  • 嘗試

    dart

(4) 緩解過拟合問題

機器學習實戰 | LightGBM模組化應用詳解
  • 使用較小的

    max_bin

  • 使用較小的

    num_leaves

  • 使用

    min_data_in_leaf

    min_sum_hessian_in_leaf

  • 通過設定

    bagging_fraction

    bagging_freq

    來使用

    bagging

  • 通過設定

    feature_fraction

    來使用特征子抽樣。
  • 使用更大的訓練資料。
  • 使用

    lambda_l1

    lambda_l2

    min_gain_to_split

    來使用正則。
  • 嘗試

    max_depth

    來避免生成過深的樹。

3.LightGBM内置模組化方式

3.1 内置模組化方式

LightGBM内置了模組化方式,有如下的資料格式與核心訓練方法:

  • 基于

    lightgbm.Dataset

    格式的資料。
  • 基于

    lightgbm.train

    接口訓練。

下面是官方的一個簡單示例,示範了讀取libsvm格式資料(成

Dataset

格式)并指定參數模組化的過程。

# coding: utf-8
import json
import lightgbm as lgb
import pandas as pd
from sklearn.metrics import mean_squared_error


# 加載資料集合
print('加載資料...')
df_train = pd.read_csv('./data/regression.train.txt', header=None, sep='\t')
df_test = pd.read_csv('./data/regression.test.txt', header=None, sep='\t')

# 設定訓練集和測試集
y_train = df_train[0].values
y_test = df_test[0].values
X_train = df_train.drop(0, axis=1).values
X_test = df_test.drop(0, axis=1).values

# 建構lgb中的Dataset格式
lgb_train = lgb.Dataset(X_train, y_train)
lgb_eval = lgb.Dataset(X_test, y_test, reference=lgb_train)

# 敲定好一組參數
params = {
    'task': 'train',
    'boosting_type': 'gbdt',
    'objective': 'regression',
    'metric': {'l2', 'auc'},
    'num_leaves': 31,
    'learning_rate': 0.05,
    'feature_fraction': 0.9,
    'bagging_fraction': 0.8,
    'bagging_freq': 5,
    'verbose': 0
}

print('開始訓練...')
# 訓練
gbm = lgb.train(params,
                lgb_train,
                num_boost_round=20,
                valid_sets=lgb_eval,
                early_stopping_rounds=5)

# 儲存模型
print('儲存模型...')
# 儲存模型到檔案中
gbm.save_model('model.txt')

print('開始預測...')
# 預測
y_pred = gbm.predict(X_test, num_iteration=gbm.best_iteration)
# 評估
print('預估結果的rmse為:')
print(mean_squared_error(y_test, y_pred) ** 0.5)
           
機器學習實戰 | LightGBM模組化應用詳解
加載資料...
開始訓練...
[1]  valid_0's l2: 0.24288   valid_0's auc: 0.764496
Training until validation scores don't improve for 5 rounds.
[2]  valid_0's l2: 0.239307  valid_0's auc: 0.766173
[3]  valid_0's l2: 0.235559  valid_0's auc: 0.785547
[4]  valid_0's l2: 0.230771  valid_0's auc: 0.797786
[5]  valid_0's l2: 0.226297  valid_0's auc: 0.805155
[6]  valid_0's l2: 0.223692  valid_0's auc: 0.800979
[7]  valid_0's l2: 0.220941  valid_0's auc: 0.806566
[8]  valid_0's l2: 0.217982  valid_0's auc: 0.808566
[9]  valid_0's l2: 0.215351  valid_0's auc: 0.809041
[10] valid_0's l2: 0.213064  valid_0's auc: 0.805953
[11] valid_0's l2: 0.211053  valid_0's auc: 0.804631
[12] valid_0's l2: 0.209336  valid_0's auc: 0.802922
[13] valid_0's l2: 0.207492  valid_0's auc: 0.802011
[14] valid_0's l2: 0.206016  valid_0's auc: 0.80193
Early stopping, best iteration is:
[9]  valid_0's l2: 0.215351  valid_0's auc: 0.809041
儲存模型...
開始預測...
預估結果的rmse為:
0.4640593794679212
           

3.2 設定樣本權重

LightGBM的模組化非常靈活,它可以支援我們對于每個樣本設定不同的權重學習,設定的方式也非常簡單,我們需要提供給模型一組權重數組資料,長度和樣本數一緻。

如下是一個典型的例子,其中

binary.train

binary.test

讀取後加載為

lightgbm.Dataset

格式的輸入,而在

lightgbm.Dataset

的建構參數中可以設定樣本權重(這個例子中是numpy array的形态)。再基于

lightgbm.train

接口使用内置模組化方式訓練。

# coding: utf-8
import json
import lightgbm as lgb
import pandas as pd
import numpy as np
from sklearn.metrics import mean_squared_error
import warnings
warnings.filterwarnings("ignore")

# 加載資料集
print('加載資料...')
df_train = pd.read_csv('./data/binary.train', header=None, sep='\t')
df_test = pd.read_csv('./data/binary.test', header=None, sep='\t')
W_train = pd.read_csv('./data/binary.train.weight', header=None)[0]
W_test = pd.read_csv('./data/binary.test.weight', header=None)[0]

y_train = df_train[0].values
y_test = df_test[0].values
X_train = df_train.drop(0, axis=1).values
X_test = df_test.drop(0, axis=1).values

num_train, num_feature = X_train.shape

# 加載資料的同時加載權重
lgb_train = lgb.Dataset(X_train, y_train,
                        weight=W_train, free_raw_data=False)
lgb_eval = lgb.Dataset(X_test, y_test, reference=lgb_train,
                       weight=W_test, free_raw_data=False)

# 設定參數
params = {
    'boosting_type': 'gbdt',
    'objective': 'binary',
    'metric': 'binary_logloss',
    'num_leaves': 31,
    'learning_rate': 0.05,
    'feature_fraction': 0.9,
    'bagging_fraction': 0.8,
    'bagging_freq': 5,
    'verbose': 0
}

# 産出特征名稱
feature_name = ['feature_' + str(col) for col in range(num_feature)]

print('開始訓練...')
gbm = lgb.train(params,
                lgb_train,
                num_boost_round=10,
                valid_sets=lgb_train,  # 評估訓練集
                feature_name=feature_name,
                categorical_feature=[21])
           
加載資料...
開始訓練...
[1]  training's binary_logloss: 0.68205
[2]  training's binary_logloss: 0.673618
[3]  training's binary_logloss: 0.665891
[4]  training's binary_logloss: 0.656874
[5]  training's binary_logloss: 0.648523
[6]  training's binary_logloss: 0.641874
[7]  training's binary_logloss: 0.636029
[8]  training's binary_logloss: 0.629427
[9]  training's binary_logloss: 0.623354
[10] training's binary_logloss: 0.617593
           

3.3 模型存儲與加載

上述模組化過程得到的模型對象,可以通過save_model成員函數進行儲存。儲存好的模型可以通過

lgb.Booster

加載回記憶體,并對測試集進行預測。

具體示例代碼如下:

# 檢視特征名稱
print('完成10輪訓練...')
print('第7個特征為:')
print(repr(lgb_train.feature_name[6]))

# 存儲模型
gbm.save_model('./model/lgb_model.txt')

# 特征名稱
print('特征名稱:')
print(gbm.feature_name())

# 特征重要度
print('特征重要度:')
print(list(gbm.feature_importance()))

# 加載模型
print('加載模型用于預測')
bst = lgb.Booster(model_file='./model/lgb_model.txt')

# 預測
y_pred = bst.predict(X_test)

# 在測試集評估效果
print('在測試集上的rmse為:')
print(mean_squared_error(y_test, y_pred) ** 0.5)
           
機器學習實戰 | LightGBM模組化應用詳解
完成10輪訓練...
第7個特征為:
'feature_6'
特征名稱:
['feature_0', 'feature_1', 'feature_2', 'feature_3', 'feature_4', 'feature_5', 'feature_6', 'feature_7', 'feature_8', 'feature_9', 'feature_10', 'feature_11', 'feature_12', 'feature_13', 'feature_14', 'feature_15', 'feature_16', 'feature_17', 'feature_18', 'feature_19', 'feature_20', 'feature_21', 'feature_22', 'feature_23', 'feature_24', 'feature_25', 'feature_26', 'feature_27']
特征重要度:
[8, 5, 1, 19, 7, 33, 2, 0, 2, 10, 5, 2, 0, 9, 3, 3, 0, 2, 2, 5, 1, 0, 36, 3, 33, 45, 29, 35]
加載模型用于預測
在測試集上的rmse為:
0.4629245607636925
           

3.4 繼續訓練

LightGBM為boosting模型,每一輪訓練會增加新的基學習器,LightGBM還支援基于現有模型和參數繼續訓練,無需每次從頭訓練。

如下是典型的示例,我們加載已經訓練10輪(即10顆樹內建)的lgb模型,在此基礎上繼續訓練(在參數層面做了一些改變,調整了學習率,增加了一些bagging等緩解過拟合的處理方法)

# 繼續訓練
# 從./model/model.txt中加載模型初始化
gbm = lgb.train(params,
                lgb_train,
                num_boost_round=10,
                init_model='./model/lgb_model.txt',
                valid_sets=lgb_eval)

print('以舊模型為初始化,完成第 10-20 輪訓練...')

# 在訓練的過程中調整超參數
# 比如這裡調整的是學習率
gbm = lgb.train(params,
                lgb_train,
                num_boost_round=10,
                init_model=gbm,
                learning_rates=lambda iter: 0.05 * (0.99 ** iter),
                valid_sets=lgb_eval)

print('逐漸調整學習率完成第 20-30 輪訓練...')

# 調整其他超參數
gbm = lgb.train(params,
                lgb_train,
                num_boost_round=10,
                init_model=gbm,
                valid_sets=lgb_eval,
                callbacks=[lgb.reset_parameter(bagging_fraction=[0.7] * 5 + [0.6] * 5)])

print('逐漸調整bagging比率完成第 30-40 輪訓練...')
           
機器學習實戰 | LightGBM模組化應用詳解
[11] valid_0's binary_logloss: 0.616177
[12] valid_0's binary_logloss: 0.611792
[13] valid_0's binary_logloss: 0.607043
[14] valid_0's binary_logloss: 0.602314
[15] valid_0's binary_logloss: 0.598433
[16] valid_0's binary_logloss: 0.595238
[17] valid_0's binary_logloss: 0.592047
[18] valid_0's binary_logloss: 0.588673
[19] valid_0's binary_logloss: 0.586084
[20] valid_0's binary_logloss: 0.584033
以舊模型為初始化,完成第 10-20 輪訓練...
[21] valid_0's binary_logloss: 0.616177
[22] valid_0's binary_logloss: 0.611834
[23] valid_0's binary_logloss: 0.607177
[24] valid_0's binary_logloss: 0.602577
[25] valid_0's binary_logloss: 0.59831
[26] valid_0's binary_logloss: 0.595259
[27] valid_0's binary_logloss: 0.592201
[28] valid_0's binary_logloss: 0.589017
[29] valid_0's binary_logloss: 0.586597
[30] valid_0's binary_logloss: 0.584454
逐漸調整學習率完成第 20-30 輪訓練...
[31] valid_0's binary_logloss: 0.616053
[32] valid_0's binary_logloss: 0.612291
[33] valid_0's binary_logloss: 0.60856
[34] valid_0's binary_logloss: 0.605387
[35] valid_0's binary_logloss: 0.601744
[36] valid_0's binary_logloss: 0.598556
[37] valid_0's binary_logloss: 0.595585
[38] valid_0's binary_logloss: 0.593228
[39] valid_0's binary_logloss: 0.59018
[40] valid_0's binary_logloss: 0.588391
逐漸調整bagging比率完成第 30-40 輪訓練...
           

3.5 自定義損失函數

LightGBM支援在訓練過程中,自定義損失函數和評估準則,其中損失函數的定義需要傳回損失函數一階和二階導數的計算方法,評估準則部分需要對資料的label和預估值進行計算。其中損失函數用于訓練過程中的樹結構學習,而評估準則很多時候是用在驗證集上進行效果評估。

# 自定義損失函數需要提供損失函數的一階和二階導數形式
def loglikelood(preds, train_data):
    labels = train_data.get_label()
    preds = 1. / (1. + np.exp(-preds))
    grad = preds - labels
    hess = preds * (1. - preds)
    return grad, hess


# 自定義評估函數
def binary_error(preds, train_data):
    labels = train_data.get_label()
    return 'error', np.mean(labels != (preds > 0.5)), False


gbm = lgb.train(params,
                lgb_train,
                num_boost_round=10,
                init_model=gbm,
                fobj=loglikelood,
                feval=binary_error,
                valid_sets=lgb_eval)

print('用自定義的損失函數與評估标準完成第40-50輪...')
           
機器學習實戰 | LightGBM模組化應用詳解
[41] valid_0's binary_logloss: 0.614429  valid_0's error: 0.268
[42] valid_0's binary_logloss: 0.610689  valid_0's error: 0.26
[43] valid_0's binary_logloss: 0.606267  valid_0's error: 0.264
[44] valid_0's binary_logloss: 0.601949  valid_0's error: 0.258
[45] valid_0's binary_logloss: 0.597271  valid_0's error: 0.266
[46] valid_0's binary_logloss: 0.593971  valid_0's error: 0.276
[47] valid_0's binary_logloss: 0.591427  valid_0's error: 0.278
[48] valid_0's binary_logloss: 0.588301  valid_0's error: 0.284
[49] valid_0's binary_logloss: 0.586562  valid_0's error: 0.288
[50] valid_0's binary_logloss: 0.584056  valid_0's error: 0.288
用自定義的損失函數與評估标準完成第40-50輪...
           

4.LightGBM預估器形态接口

4.1 SKLearn形态預估器接口

和XGBoost一樣,LightGBM也支援用SKLearn中統一的預估器形态接口進行模組化,如下為典型的參考案例,對于讀取為Dataframe格式的訓練集和測試集,可以直接使用LightGBM初始化

LGBMRegressor

進行fit拟合訓練。使用方法與接口,和SKLearn中其他預估器一緻。

# coding: utf-8
import lightgbm as lgb
import pandas as pd
from sklearn.metrics import mean_squared_error
from sklearn.model_selection import GridSearchCV

# 加載資料
print('加載資料...')
df_train = pd.read_csv('./data/regression.train.txt', header=None, sep='\t')
df_test = pd.read_csv('./data/regression.test.txt', header=None, sep='\t')

# 取出特征和标簽
y_train = df_train[0].values
y_test = df_test[0].values
X_train = df_train.drop(0, axis=1).values
X_test = df_test.drop(0, axis=1).values

print('開始訓練...')
# 初始化LGBMRegressor
gbm = lgb.LGBMRegressor(objective='regression',
                        num_leaves=31,
                        learning_rate=0.05,
                        n_estimators=20)

# 使用fit函數拟合
gbm.fit(X_train, y_train,
        eval_set=[(X_test, y_test)],
        eval_metric='l1',
        early_stopping_rounds=5)

# 預測
print('開始預測...')
y_pred = gbm.predict(X_test, num_iteration=gbm.best_iteration_)
# 評估預測結果
print('預測結果的rmse是:')
print(mean_squared_error(y_test, y_pred) ** 0.5)
           
機器學習實戰 | LightGBM模組化應用詳解
加載資料...
開始訓練...
[1]  valid_0's l1: 0.491735
Training until validation scores don't improve for 5 rounds.
[2]  valid_0's l1: 0.486563
[3]  valid_0's l1: 0.481489
[4]  valid_0's l1: 0.476848
[5]  valid_0's l1: 0.47305
[6]  valid_0's l1: 0.469049
[7]  valid_0's l1: 0.465556
[8]  valid_0's l1: 0.462208
[9]  valid_0's l1: 0.458676
[10] valid_0's l1: 0.454998
[11] valid_0's l1: 0.452047
[12] valid_0's l1: 0.449158
[13] valid_0's l1: 0.44608
[14] valid_0's l1: 0.443554
[15] valid_0's l1: 0.440643
[16] valid_0's l1: 0.437687
[17] valid_0's l1: 0.435454
[18] valid_0's l1: 0.433288
[19] valid_0's l1: 0.431297
[20] valid_0's l1: 0.428946
Did not meet early stopping. Best iteration is:
[20] valid_0's l1: 0.428946
開始預測...
預測結果的rmse是:
0.4441153344254208
           

4.2 網格搜尋調參

上面提到LightGBM的預估器接口,整體使用方法和SKLearn中其他預估器一緻,是以我們也可以使用SKLearn中的超參數調優方法來進行模型調優。

如下是一個典型的網格搜尋交法調優超參數的代碼示例,我們會給出候選參數清單字典,通過

GridSearchCV

進行交叉驗證明驗評估,選出LightGBM在候選參數中最優的超參數。

# 配合scikit-learn的網格搜尋交叉驗證選擇最優超參數
estimator = lgb.LGBMRegressor(num_leaves=31)

param_grid = {
    'learning_rate': [0.01, 0.1, 1],
    'n_estimators': [20, 40]
}

gbm = GridSearchCV(estimator, param_grid)

gbm.fit(X_train, y_train)

print('用網格搜尋找到的最優超參數為:')
print(gbm.best_params_)
           
機器學習實戰 | LightGBM模組化應用詳解
用網格搜尋找到的最優超參數為:
{'learning_rate': 0.1, 'n_estimators': 40}
           

4.3 繪圖解釋

LightGBM支援對模型訓練進行可視化呈現與解釋,包括對于訓練過程中的損失函數取值與評估準則結果的可視化、訓練完成後特征重要度的排序與可視化、基學習器(比如決策樹)的可視化。

以下為參考代碼:

# coding: utf-8
import lightgbm as lgb
import pandas as pd

try:
    import matplotlib.pyplot as plt
except ImportError:
    raise ImportError('You need to install matplotlib for plotting.')

# 加載資料集
print('加載資料...')
df_train = pd.read_csv('./data/regression.train.txt', header=None, sep='\t')
df_test = pd.read_csv('./data/regression.test.txt', header=None, sep='\t')

# 取出特征和标簽
y_train = df_train[0].values
y_test = df_test[0].values
X_train = df_train.drop(0, axis=1).values
X_test = df_test.drop(0, axis=1).values

# 建構lgb中的Dataset資料格式
lgb_train = lgb.Dataset(X_train, y_train)
lgb_test = lgb.Dataset(X_test, y_test, reference=lgb_train)

# 設定參數
params = {
    'num_leaves': 5,
    'metric': ('l1', 'l2'),
    'verbose': 0
}

evals_result = {}  # to record eval results for plotting

print('開始訓練...')
# 訓練
gbm = lgb.train(params,
                lgb_train,
                num_boost_round=100,
                valid_sets=[lgb_train, lgb_test],
                feature_name=['f' + str(i + 1) for i in range(28)],
                categorical_feature=[21],
                evals_result=evals_result,
                verbose_eval=10)

print('在訓練過程中繪圖...')
ax = lgb.plot_metric(evals_result, metric='l1')
plt.show()

print('畫出特征重要度...')
ax = lgb.plot_importance(gbm, max_num_features=10)
plt.show()

print('畫出第84顆樹...')
ax = lgb.plot_tree(gbm, tree_index=83, figsize=(20, 8), show_info=['split_gain'])
plt.show()

#print('用graphviz畫出第84顆樹...')
#graph = lgb.create_tree_digraph(gbm, tree_index=83, name='Tree84')
#graph.render(view=True)
           
機器學習實戰 | LightGBM模組化應用詳解
加載資料...
開始訓練...
[10] training's l2: 0.217995 training's l1: 0.457448 valid_1's l2: 0.21641   valid_1's l1: 0.456464
[20] training's l2: 0.205099 training's l1: 0.436869 valid_1's l2: 0.201616  valid_1's l1: 0.434057
[30] training's l2: 0.197421 training's l1: 0.421302 valid_1's l2: 0.192514  valid_1's l1: 0.417019
[40] training's l2: 0.192856 training's l1: 0.411107 valid_1's l2: 0.187258  valid_1's l1: 0.406303
[50] training's l2: 0.189593 training's l1: 0.403695 valid_1's l2: 0.183688  valid_1's l1: 0.398997
[60] training's l2: 0.187043 training's l1: 0.398704 valid_1's l2: 0.181009  valid_1's l1: 0.393977
[70] training's l2: 0.184982 training's l1: 0.394876 valid_1's l2: 0.178803  valid_1's l1: 0.389805
[80] training's l2: 0.1828   training's l1: 0.391147 valid_1's l2: 0.176799  valid_1's l1: 0.386476
[90] training's l2: 0.180817 training's l1: 0.388101 valid_1's l2: 0.175775  valid_1's l1: 0.384404
[100]   training's l2: 0.179171 training's l1: 0.385174 valid_1's l2: 0.175321  valid_1's l1: 0.382929
           
機器學習實戰 | LightGBM模組化應用詳解
機器學習實戰 | LightGBM模組化應用詳解

參考資料

  • 圖解機器學習算法 | 從入門到精通系列
  • 圖解機器學習 | LightGBM模型詳解

機器學習【算法】系列教程

  • 圖解機器學習 | 機器學習基礎知識
  • 圖解機器學習 | 模型評估方法與準則
  • 圖解機器學習 | KNN算法及其應用
  • 圖解機器學習 | 邏輯回歸算法詳解
  • 圖解機器學習 | 樸素貝葉斯算法詳解
  • 圖解機器學習 | 決策樹模型詳解
  • 圖解機器學習 | 随機森林分類模型詳解
  • 圖解機器學習 | 回歸樹模型詳解
  • 圖解機器學習 | GBDT模型詳解
  • 圖解機器學習 | XGBoost模型最全解析
  • 圖解機器學習 | LightGBM模型詳解
  • 圖解機器學習 | 支援向量機模型詳解
  • 圖解機器學習 | 聚類算法詳解
  • 圖解機器學習 | PCA降維算法詳解

機器學習【實戰】系列教程

  • 機器學習實戰 | Python機器學習算法應用實踐
  • 機器學習實戰 | SKLearn入門與簡單應用案例
  • 機器學習實戰 | SKLearn最全應用指南
  • 機器學習實戰 | XGBoost模組化應用詳解
  • 機器學習實戰 | LightGBM模組化應用詳解
  • 機器學習實戰 | Python機器學習綜合項目-電商銷量預估
  • 機器學習實戰 | Python機器學習綜合項目-電商銷量預估<進階方案>
  • 機器學習實戰 | 機器學習特征工程最全解讀
  • 機器學習實戰 | 自動化特征工程工具Featuretools應用
  • 機器學習實戰 | AutoML自動化機器學習模組化

ShowMeAI系列教程推薦

  • 大廠技術實作方案系列
  • 圖解Python程式設計:從入門到精通系列教程
  • 圖解資料分析:從入門到精通系列教程
  • 圖解AI數學基礎:從入門到精通系列教程
  • 圖解大資料技術:從入門到精通系列教程
  • 圖解機器學習算法:從入門到精通系列教程
  • 機器學習實戰:手把手教你玩轉機器學習系列
  • 深度學習教程:吳恩達專項課程 · 全套筆記解讀
  • 自然語言處理教程:斯坦福CS224n課程 · 課程帶學與全套筆記解讀
  • 深度學習與計算機視覺教程:斯坦福CS231n · 全套筆記解讀
機器學習實戰 | LightGBM模組化應用詳解

繼續閱讀