r - 如何替换包 randomForest r 中的引导步骤

标签 r function edit random-forest statistics-bootstrap

首先是一些背景信息,这在 stats.stackexchange 上可能更有趣:

在我的数据分析中,我尝试比较不同机器学习方法对时间序列数据(回归,而不是分类)的性能。例如,我训练了一个 Boosting 训练模型,并将其与随机森林训练模型(R 包 randomForest)进行了比较。

我使用时间序列数据,其中解释变量是其他数据和因变量的滞后值。

出于某种原因,随机森林的表现严重不佳。我能想到的问题之一是随机森林对每棵树的训练数据执行一个采样步骤。如果它对时间序列数据执行此操作,则该序列的自回归性质将被完全消除。

为了测试这个想法,我想用所谓的按块引导步骤替换 randomForest() 函数中的(引导)采样步骤。这基本上意味着我将训练集切成 k 个部分,其中 k<<N ,其中每个第 k 部分都按原始顺序排列。如果我对这 k 个部分进行采样,我仍然可以从随机森林中的“随机性”中受益,但时间序列的性质基本保持不变。

现在我的问题是这样的:

为此,我通常会复制现有函数并编辑所需的步骤/行。

randomForest2 <- randomForest()

但是 randomForest() 函数似乎是另一个包装器的包装器,用于更深层次的底层功能。那么如何在 randomForest() 函数中编辑实际的引导步骤,并仍然定期运行该函数的其余部分?

最佳答案

所以对我来说,解决方案不是编辑现有的 randomForest 函数。相反,我使用 split2 自己编写了逐块 bootstrap 。 Soren H. Welling 给出的函数来创建块。一旦我的数据块级引导,我寻找一个包( rpart ),它只执行一个回归树并自己聚合(采取手段)。

我的实际数据的结果是在 RMSPE 方面比正常随机森林性能略有但持续改进的版本。

对于下面的代码,性能似乎是掷硬币。

以 Soren 的代码为例,它看起来有点像这样:

library(randomForest)
library(doParallel) #parallel package and mclapply is better for linux
library(rpart)

#parallel backend ftw
nCPU = detectCores()
cl = makeCluster(nCPU)
registerDoParallel(cl)

#simulated time series(y) with time roll and lag=1
timepoints=1000;var=6;noise.factor=.2

#past to present orientation    
y = sin((1:timepoints)*pi/30) * 1000 +
  sin((1:timepoints)*pi/40) * 1000 + 1:timepoints
y = y+rnorm(timepoints,sd=sd(y))*noise.factor
plot(y,type="l")

#convert to absolute change, with lag=1
dy = c(0,y[-1]-y[-length(y)]) # c(0,t2-t1,t3-t2,...)

#compute lag 
dy = dy + rnorm(timepoints)*sd(dy)*noise.factor #add noise
dy = c(0,y[-1]-y[-length(y)]) #convert to absolute change, with lag=1 
dX = sapply(1:40,function(i){
  getTheseLags = (1:timepoints) - i
  getTheseLags[getTheseLags<1] = NA #remove before start timePoints
  dx.lag.i = dy[getTheseLags]
})
dX[is.na(dX)]=-100 #quick fix of when lag exceed timeseries
pairs(data.frame(dy,dX[,1:5]),cex=.2)#data structure

#make train- and test-set
train=1:600
dy.train = dy[ train]
dy.test  = dy[-train]
dX.train  = dX[ train,]
dX.test   = dX[-train,]

#classic rf
rf = randomForest(dX.train,dy.train,ntree=500)
print(rf)

#like function split for a vector without mixing
split2 = function(aVector,splits=31) {
  lVector = length(aVector)
  mod = lVector %% splits
  lBlocks = rep(floor(lVector/splits),splits)
  if(mod!=0) lBlocks[1:mod] = lBlocks[1:mod] + 1
  lapply(1:splits,function(i) {
    Stop  = sum(lBlocks[1:i])
    Start = Stop - lBlocks[i] + 1
    aVector[Start:Stop]
  })
}  


#create a list of block-wise bootstrapped samples
aBlock <- list()
numTrees <- 500
splits <- 40
for (ttt in 1:numTrees){

  aBlock[[ttt]] <- unlist(
    sample(
      split2(1:nrow(dX.train),splits=splits),
      splits,
      replace=T
    )
  )
}

#put data into a dataframe so rpart understands it
df1 <- data.frame(dy.train, dX.train)
#perform regression trees for Blocks
rfBlocks = foreach(aBlock = aBlock,
                   .packages=("rpart")) %dopar% {
                     dBlock = df1[aBlock,] 
                     rf = predict( rpart( dy.train ~., data = dBlock, method ="anova" ), newdata=data.frame(dX.test) ) 
                   } 

#predict test, make results table
#use rowMeans to aggregate the block-wise predictions
results = data.frame(predBlock   = rowMeans(do.call(cbind.data.frame, rfBlocks)),
                     true=dy.test,
                     predBootstrap = predict(rf,newdata=dX.test)
                     )
plot(results[,1:2],xlab="OOB-CV predicted change",
     ylab="trueChange",
     main="black bootstrap and blue block train")
points(results[,3:2],xlab="OOB-CV predicted change",
       ylab="trueChange",
       col="blue")

#prediction results
print(cor(results)^2)


stopCluster(cl)#close cluster

关于r - 如何替换包 randomForest r 中的引导步骤,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32057569/

相关文章:

c - 修改c中文件的现有内容

c - 如何在 C 中编辑文本文件中行的特定部分?

java - jQGrid 编辑中的行锁定

r - 检测向量中的第 n 次重复(和第 n+1 次,...)

r - GoogleAnalyticsR api - FilterExpression

python - Pandas 聚合函数输出到 xlsx

JSP 中未调用 Javascript 函数

function - 如何直接将函数返回的多个值相加

r - 将不同长度的向量合并为动态矩阵

r - 在 R 中循环多个变量