使用caret
库中的train
在 R 中训练模型时是否可以指定超时? 如果不存在,是否存在包装代码并且可以在一定时间后终止的 R 构造?
插入符号选项配置了trainControl()
对象。它没有用于指定超时期限的参数。
trainControl()
中对运行时性能影响最大的两个设置是method=
和number=
。插入符号中的默认方法是boot
或引导。引导方法的默认number
为 25,除非method="cv"
。
因此,使用 Caret 运行的randomForest
将执行 25 次引导示例迭代,这是一个非常缓慢的过程,尤其是在单个处理器线程上运行时。
强制超时
可以通过R.utils
包中的withTimeout()
函数为 R 函数指定超时期限。
例如,我们将使用 mtcars 数据集通过插入符号运行一个随机森林,并执行 500 次引导采样迭代,以使train()
运行时间超过 15 秒。我们将使用withTimeout()
在 CPU 时间 15 秒后停止处理。
data(mtcars)
library(randomForest)
library(R.utils)
library(caret)
fitControl <- trainControl(method = "boot",
number = 500,
allowParallel = FALSE)
withTimeout(
theModel <- train(mpg ~ .,data=mtcars,method="rf",trControl=fitControl)
,timeout=15)
。和输出的第一部分:
> withTimeout(
+ theModel <- train(mpg ~ .,data=mtcars,method="rf",trControl=fitControl)
+ ,timeout=15)
[2018-05-19 07:32:37] TimeoutException: task 2 failed - "reached elapsed time limit" [cpu=15s, elapsed=15s]
提高caret
性能
除了简单地超时caret::train()
函数外,我们还可以使用两种技术来提高caret::train()
的性能,并行处理和调整trainControl()
参数。
- 编写 R 脚本以使用并行处理需要
parallel
和doParallel()
包,并且是一个多步骤过程。 - 将
method="boot"
更改为method="cv"
(k-fold交叉验证(并将number=
减少到3
或5
将显着提高caret::train()
的运行时性能。
总结我之前在使用 caret::train(( 提高随机森林的性能中描述的技术,以下代码使用Sonar
数据集来实现具有caret
和randomForest
的并行处理。
#
# Sonar example from caret documentation
#
library(mlbench)
library(randomForest) # needed for varImpPlot
data(Sonar)
#
# review distribution of Class column
#
table(Sonar$Class)
library(caret)
set.seed(95014)
# create training & testing data sets
inTraining <- createDataPartition(Sonar$Class, p = .75, list=FALSE)
training <- Sonar[inTraining,]
testing <- Sonar[-inTraining,]
#
# Step 1: configure parallel processing
#
library(parallel)
library(doParallel)
cluster <- makeCluster(detectCores() - 1) # convention to leave 1 core for OS
registerDoParallel(cluster)
#
# Step 2: configure trainControl() object for k-fold cross validation with
# 5 folds
#
fitControl <- trainControl(method = "cv",
number = 5,
allowParallel = TRUE)
#
# Step 3: develop training model
#
system.time(fit <- train(Class ~ ., method="rf",data=Sonar,trControl = fitControl))
#
# Step 4: de-register cluster
#
stopCluster(cluster)
registerDoSEQ()
#
# Step 5: evaluate model fit
#
fit
fit$resample
confusionMatrix.train(fit)
#average OOB error from final model
mean(fit$finalModel$err.rate[,"OOB"])
plot(fit,main="Accuracy by Predictor Count")
varImpPlot(fit$finalModel,
main="Variable Importance Plot: Random Forest")
sessionInfo()