累計

  • 156,636 pv

アクセスカウンター

機械学習 プログラミング

【機械学習】【R】Rでのデータ分析(4)Randomforest,XGboost、アンサンブル学習 ー銀行の顧客ターゲティング【SIGNATE】ー

 

どうも、solobochiのbochiです。

 

昨年、データサイエンティスト協会主催のデータサイエンティスト養成講座を受講し、その中でRを使ったデータ分析手法を学んだのでその復習兼ねてまとめておきます。

 

データサイエンティスト養成講座 2019年9月開講決定

 

 



 

 

目次

    1. 概要(※前回記事参照)
    2. データセット(※前回記事参照)
    3. データ分析(※前回記事参照)
    4. 前処理(※前回記事参照)
    5. モデル構築
    6. 予測
    7. 評価

 

 

5.モデル構築

前回記事↓まででデータ分析で最も手間のかかる前処理工程及び決定木での分析まで実施したので、同様にランダムフォレスト、XGBoostでの分析を実施する。

 

【機械学習】【R】Rでのデータ分析(3)決定木 ー銀行の顧客ターゲティング【SIGNATE】ー

 

 

 

ランダムフォレスト(RandomForest)

# RandomForest
# 構築データの割合
rate <- 0.75

# 構築データ数(小数の切捨て)
num1 <- as.integer(nrow(train_data_ohe3)*rate)

# 再現性のため乱数シードを固定
set.seed(17)

# sample(ベクトル, ランダムに取得する個数, 復元抽出の有無)
row1 <- sample(1:nrow(train_data_ohe3), num1, replace=FALSE)

# 学習データ
rf_train_train <- train_data_ohe3[row1,] %>%
  dplyr::select(-y)
y_train_train <- train_data_ohe3[row1,] %>%
  dplyr::select(y)

# 検証データ
rf_train_test <- train_data_ohe3[-row1,] %>%
  dplyr::select(-y)
y_train_test <- train_data_ohe3[-row1,] %>%
  dplyr::select(y)

# モデル構築(学習)
rf <-  randomforest(rf_train_train,             #学習データ(説明変数)
                    as.factor(rf_train_train$y),     #学習データ(目的変数)
                    mtry=12,                 #1本の木に使う特徴量の数(パラメータチューニングで最適化する)
            sampsize=nrow(rf_train_train)*0.25, #各決定木に使うデータ数
                    nodesize=20,               #各決定木のノードが含むサンプルデータ最小数
            maxnode=150,               #各決定木のノードが含むサンプルデータ最大数
            ntree=90,                 #決定木の数
            importance=T)

# モデルの確認
rf

# 変数重要度
print(importance(rf)

 

使ったコマンド

randomforest
使用目的:ランダムフォレストモデルの構築(学習)
使用方法:randomforest(dataframe(説明変数),
              y(目的変数),
mtry(各決定木に用いる特徴量の数),
sampsize(モデル構築に用いるデータ数),
nodesize(各決定木の終端ノードにおける最小サンプル数),
maxnode(各決定木の終端ノードにおける最大サンプル数),
ntree(生成する決定木の数),
importance(変数重要度の有無),
)

 

👉OOB(Out-Of-Bag):10.05%ということで、学習時点でモデルの予測エラー率は約10%

 

👉変数重要度。durationが圧倒的に高い点は決定木と同じ結果。

 

 

これをテストデータにも適用させて精度を検証する。

# predict
pred_rf <- predict(rf, rf_train_test, type="prob")[,2]

# auc
auc_rf <- roc(y_train_test, pred_rf)
print(auc_rf)

 

👉AUCは0.91とまずまずの値となりました。

 

 



 

 

さらにXGBoostでも分析を実施する。

※XGBoost:eXtremely Gradient Boosting。RandomForestとGradientBoostingをアンサンブル学習させた勾配ブースティング決定木のライブラリ。

 

XGBoost

# xgboost
# 行列に変換
x_train_xgb <- as.matrix(dplyr::select(train_data_ohe3, -y))
x_test_xgb <- as.matrix(dplyr::select(test_data_ohe3))

# 目的変数(学習データのみ)
y_train_xgb <- train_data_ohe3$y

# Hold out
# 構築データの割合
rate <- 0.7

# 構築データ数
num2 <- as.integer(nrow(x_train_xgb)*rate)
set.seed(17)

# 学習データ
row2 <- sample(1:nrow(x_train_xgb), num2, replace=FALSE)
xgb_train_train <- x_train_xgb[row2,] #訓練データ
xgb_train_test <- x_train_xgb[-row2,] #検証データ
y_train_train <- y_train_xgb[row2,]  #訓練データの目的変数
y_train_test <- y_train_xgb[-row2,]  #検証データの目的変数

# パラメータ設定
parm <- list(objective="binary:logistic",  #学習方法(binary:logisticは2クラス分類の確率で出力)
        eval_metric = "auc",          #評価指標(validation)
        eta = 0.07,            #学習率(ステップごとの学習幅)
        max_depth = 10,         #決定木の階層数
        min_child_weight = 10,     #最小ノード数(これを下回ると分割を止める)
        colsample_bytree = 0.4,     #各決定木を作る際に使う列数をサンプリングする割合
        gamma = 0.9,           #損失還元最小値(決定木の葉の数に対するペナルティ、過学習の抑制)
        subsample = 1          #学習に使用するデータ(標本)の割合
)

#xgb.cv(Cross Validation)による最適パラメータ探索(nrounds:ブースティング回数、決定木の本数を最適化する)
xgbcv <- xgb.cv(param = parm,                   #パラメータ(objective,eval_metric,eta,max_depthなど)
              data = x_train_train,    #訓練データ
              label = y_train_train,  #目的変数
              nrounds = 400,       #施行回数
              nfold = 10,         #分割数
              nthread = 1         #使用CPU数
)

# モデル構築
model_xgb <- xgboost(param = parm,             #パラメータ
             data = x_train_train,     #訓練データ
             label = y_train_train,    #目的変数
             nrounds = which.max(xgbcv$evaluation_log$test_auc_mean),
             nthread = 1,         
             importance = True
)

# train_testのauc
pred_xgb <- predict(model_xgb, x_train_test)
auc_xgb <- roc(y_train_test, pred_xgb)
print(auc_xgb)

 

使ったコマンド

xgboost
使用目的:xgboostのモデル構築
使用方法:xgboost(param, data, label, nrounds, nthread, importance)
※param = objective, eval_metric, eta, max_depth, min_child_weight, colsample_bytree, gamma, subsample

xgboostのパラメータの詳細についてはこちらのリファレンス参照。
xgboostリファレンス

 

👉AUCは92.3%となり、RandomForestよりも若干良いスコアになりました。

 

 



 

 

6.予測と結果

続いて、ここまで作成してきたモデルを使ってコンペ用のデータに対して予測を行います。

 

 

決定木

# submit
test_pred_tree <- predict(tree2, test_data_ohe3)
test_pred_tree <- test_pred_tree[,2]

# CSV出力(コンペ提出の形式)
out_tree <- data.frame(test_data_ohe3$id, test_pred_tree)
write.table(out_tree,                   #出力データ
       "/Users/xxxxx/xxxxx.csv",   #任意のディレクトリ配下に出力ファイルを作成
       quote = FALSE ,             #文字列を""で囲むかどうか
       col.names = FALSE,          #変数名の有無
       row.names = FALSE,          #行番号の有無
       sep = ','                   #区切り文字の設定
)

 

これで作成されるファイルを投稿すれば提出すれば完了。

決定木のデータでの精度は、およそ75%でした。

 

 

続いてランダムフォレストでもやってみる。

 

RandomForest

# submit
# predict
pred_test_rf <- predict(rf, test_data_ohe3, type="prob")
pred_test_rf <- pred_test_rf[,2]

# submit形式に出力
submit_rf <- data.frame(test_data_ohe3$id, pred_test_rf)

write.table(submit_rf,           #出力データ
            "/Users/xxx/xxx.csv",
            quote = FALSE,       
            col.names = FALSE,
            row.names = FALSE,
            sep = ","
)

👉ランダムフォレストの結果、精度が91.3%に向上しました。

 

最後にxgboostでも同様に予測、投稿して結果を検証する。

 

 

XGBoost

# submit
# predict
x_test_xgb <- as.matrix(dplyr::select(test_data_ohe3, -id))
pred_test_xgb <- predict(model_xgb, x_test_xgb, type="response")
pred_test_xgb <- pred_test_xgb[,2]

# submit形式に出力
submit_xgb <- data.frame(test_data_ohe3$id, pred_test_xgb)

write.table(submit_xgb,           #出力データ
            "/Users/xxx/xxx.csv",
            quote = FALSE,       
            col.names = FALSE,
            row.names = FALSE,
            sep = ","
)

 

👉精度が92.4%へと向上しました。

 

決定木(75%) < RandomForest(91.3%) < XGBoost(92.4%)

という結果になりました。

 

 

最後に、これらの結果をアンサンブル学習させてみます。

# colname
names(out_tree2)[which(names(out_tree2)=="test_data_ohe3.id")] <- "id"
names(out_tree2)[which(names(out_tree2)=="test_pred_tree")] <- "pred_tree"
names(submit_rf2)[which(names(submit_rf2)=="test_data_ohe3.id")] <- "id"
names(submit_rf2)[which(names(submit_rf2)=="pred_test_rf2")] <- "pred_rf"
names(submit_xgb2)[which(names(submit_xgb2)=="test_data_ohe3.id")] <- "id"
names(submit_xgb2)[which(names(submit_xgb2)=="pred_test_xgb")] <- "pred_xgb"

# merge
submit_tr_rf <- merge(out_tree2, submit_rf2, by = "id")
submit_tr_rf_xgb <- merge(submit_tr_rf, submit_xgb2, by = "id")

# ensemble
submit_tr_rf_xgb <- mutate(submit_tr_rf_xgb, mean1 = (pred_tree*0.05 + pred_rf*0.15 + pred_xgb*0.8))
collist1 <- c("id","mean1")
submit_en1 <- submit_tr_rf_xgb[,collist1]

# submit形式に出力
write.table(submit_en1,           #出力データ
            "/Users/xxx/xxx.csv",
       quote = FALSE,
       col.names = FALSE,
       row.names = FALSE,
       sep = ','       
)

👉わずかですが、xgboost単体から92.5%まで精度向上しました。

 

 



 

 

7.評価

これまでの結果をまとめると以下の通り。

 

まず手元の学習データでの精度は、

・決定木 74.4%

・RandomForest 91%

・XGBoost 92.3%

 

 

続いて投稿した未知のデータでの精度では、

・決定木 75%

・RandomForest 91.3%

・XGBoost 92.4%

・アンサンブル 92.5%

 

となりました。

 

 

 

 

 

 

 

以上

 

 

 

 

  • この記事を書いた人
  • 最新記事

solobochi

(名前):solobochi

(説明)
独身アラサー男子
国内大手IT企業中堅社員。
プログラミングやセミナーのアウトプットがしたいと思いブログを開設。
プロジェクトマネジメント関連の資格やディープラーニング、機械学習系の資格取得ノウハウについても発信。


(Like)
・最適化することが好き
・PDCAを回すのが好き


(当サイト)
日々思うことを徒然と発信
└(例)
・学びのアウトプット
・投資・資産運用
・プログラミング
・資格試験の対策
・セミナーのレビュー
・書評
etc...


詳しくは自己紹介記事にて。
自己紹介①
自己紹介②
自己紹介③
自己紹介④

-機械学習, プログラミング
-, , , , , ,

Copyright© そろボチ , 2023 All Rights Reserved Powered by AFFINGER5.