いくつかのランダムフォレスト(回帰用)をトレーニングして、それらを競合させ、どの機能選択とどのパラメーターが最良のモデルを与えるかを確認しようとしています。
しかし、トレーニングには非常に時間がかかるようで、何か間違っているのではないかと思っています。
私がトレーニングに使用しているデータセット(以下のtrain
と呼ばれます)には、217k行と58列(そのうちの21のみがランダムフォレストで予測子として機能します。ブール値のものを除いて、これらはすべてnumeric
またはinteger
です。クラスはcharacter
です。y
の出力はnumeric
です)。
次のコードを4回実行し、_4
_、_100
_、_500
_、_2000
_から_nb_trees
_の値を指定しました。
_library("randomForest")
nb_trees <- #this changes with each test, see above
ptm <- proc.time()
fit <- randomForest(y ~ x1 + x2 + x3 + x4 + x5 + x6 + x7 + x8 + x9
+ x10 + x11 + x12 + x13 + x14 + x15 + x16 + x17 + x18 + x19
+ x20 + x21,
data = train,
ntree = nb_trees,
do.trace=TRUE)
proc.time() - ptm
_
それぞれがトレーニングにかかった時間は次のとおりです。
_nb_trees | time
4 4mn
100 1h 41mn
500 8h 40mn
2000 34h 26mn
_
私の会社のサーバーには12コアと125 GoのRAMがあるので、トレーニングを並列化してみようと思った この答え (ただし、doParallel
パッケージを使用したのは、doSNOW
で永久に実行されているようだったからです。理由はわかりません。また、doParallel
も機能することを確認できませんでした(申し訳ありません)。
_library("randomForest")
library("foreach")
library("doParallel")
nb_trees <- #this changes with each test, see table below
nb_cores <- #this changes with each test, see table below
cl <- makeCluster(nb_cores)
registerDoParallel(cl)
ptm <- proc.time()
fit <- foreach(ntree = rep(nb_trees, nb_cores), .combine = combine, .packages = "randomForest")
%dopar% {
randomForest(y ~ x1 + x2 + x3 + x4 + x5 + x6 + x7 + x8 + x9
+ x10 + x11 + x12 + x13 + x14 + x15 + x16 + x17 + x18 + x19
+ x20 + x21,
data = train,
ntree = ntree,
do.trace=TRUE)}
proc.time() - ptm
stopCluster(cl)
_
実行すると、並列化されていないコードよりも時間がかかります:
_nb_trees | nb_cores | total number of trees | time
1 4 4 2mn13s
10 10 100 52mn
9 12 108 (closest to 100 with 12 cores) 59mn
42 12 504 (closest to 500 with 12 cores) I won't be running this one
167 12 2004 (closest to 2000 with 12 cores) I'll run it next week-end
_
でも、まだ時間がかかると思いますね。木を組み合わせて最終的なフォレストにするのに時間がかかることは承知しているので、12コアで12倍高速になるとは思っていませんでしたが、わずか2倍高速です...
ご回答ありがとうございます。
ノート :
randomForest(predictors,decision)
の代わりにrandomForest(decision~.,data=input)
を呼び出すことで実行時間を改善できることにかなり遅れて気づきました。これからもそれを実行しますが、上記の質問はまだ残っていると思います。私は、並列化や非常に長い時間コードを実行するなどのブルートフォーステクニックのファンですが、ブルートフォーステクニックを使用する必要がないようにアルゴリズムを改善するというより大きなファンです。
2000本の木を使用してランダムフォレストをトレーニングすることは法外に高価になり始めていましたが、より少ない本数の木を使用したトレーニングはより合理的な時間を要しました。まず第一に、あなたは言う4
、8
、16
、32
、...
、256
、512
ツリーを使用して、モデルの堅牢性を知らせるメトリックを注意深く観察します。これらのメトリクスには、最適な定数モデル(データセットでフォレストがどの程度うまく機能するか、すべての入力の中央値を予測するモデルなど)、およびout-of-bagエラーが含まれます。さらに、上位の予測子とその重要性、およびツリーを追加するときにそこに収束が見られるかどうかを確認できます。
理想的には、モデルを構築するために何千ものツリーを使用する必要はないはずです。モデルが収束し始めたら、ツリーを追加しても必ずしもモデルが悪化するわけではありませんが、同時に新しい情報は追加されません。あまりにも多くの木を使用しないようにすることで、1週間から1日未満の計算を削減できる場合があります。これに加えて、数十のCPUコアを活用している場合は、何時間も何かを調べている可能性があります。
ランダムフォレストを実行するたびに変数の重要度を確認するには、次のように試してみます。
fit <- randomForest(...)
round(importance(fit), 2)
最初の5〜10の予測子がモデルに最も大きな影響を与えると私は理解しています。ツリーを増やしても、これらの上位予測子は実際には相対的な位置を変更せず、重要度の指標は同じであるように見える場合は、それほど多くのツリーを使用しないことを検討してください。
randomForest()
関数は、「式インターフェース」または「マトリックスインターフェース」のいずれかを使用してデータを受け入れることができます。マトリックスインターフェイスは、より優れたパフォーマンス値を提供することが知られています。
数式インターフェース:
rf.formula = randomForest(Species ~ ., data = iris)
マトリックスインターフェイス:
rf.matrix = randomForest(y = iris[, 5], x = iris[, 1:4])