如何在for循环中存储for循环的数据? (r中的滚动相关)

时间:2016-07-21 14:00:42

标签: r loops lapply datastore

require(quantmod)
require(TTR)

iris2 <- iris[1:4]
b=NULL
for (i in 1:ncol(iris2)){
for (j in 1:ncol(iris2)){
a<- runCor(iris2[,i],iris2[,j],n=21)
b<-cbind(b,a)}}

我想计算数据框中不同列的滚动关联,并按列分别存储数据。虽然上面的代码将数据存储到变量b中,但它并不像转储所有结果那样有用。我想要的是能够为每个i创建不同的数据帧。

在这种情况下,由于我有4列,我最终想要的是4个数据帧,每个数据帧包含4列显示滚动相关性,即df1 = col 1的col 1与col 1,2,3,4,df2 = corr col 2 vs col 1,2,3,4 ......等等)

我想过使用lapply或rollapply,但遇到了同样的问题。

d=NULL
for (i in 1:ncol(iris2))
 for (j in 1:ncol(iris2))
{c<-rollapply(iris2, 21 ,function(x) cor(x[,i],x[,j]), by.column=FALSE)
d<-cbind(d,c)}  

非常感谢任何投入。

3 个答案:

答案 0 :(得分:2)

如果你想保留扩展循环,那么数据帧列表呢?

e <- list(length = length(ncol(iris2)))

for (i in 1:ncol(iris2)) {
  d <- matrix(0, nrow = length(iris2[,1]), ncol = length(iris2[1,]))
    for (j in 1:ncol(iris2)) {
        d[,j]<- runCor(iris2[,i],iris2[,j],n=21)
    }
e[[i]] <- d
}

使用占位符分配所需的空间量并将项目放入该空间而不是使用rbindcbind也是一个好主意。

答案 1 :(得分:2)

虽然是在R中动态创建数据帧的好习惯(您应该像在其他答案中那样将它们放在列表中),但这样做的方法是使用{ {1}}和assign函数。

get

答案 2 :(得分:1)

由于您说您的计算速度很慢,我想为您提供并行解决方案。如果你有一台现代计算机,它可能有2个内核,如果不是4个(或更多!)。您可以通过以下方式轻松查看:

require(parallel) # for parallelization
detectCores()

现在代码:

require(quantmod)
require(TTR)

iris2 <- iris[,1:4]

并行化要求将函数和变量放入每个进程创建和销毁的特殊环境中。这意味着必须创建一个包装函数来定义变量和函数。

wrapper <- function(data, n) {
  # variables placed into environment
  force(data)
  force(n)

  # functions placed into environment
  # same inner loop written in earlier answer
  runcor <- function(data, n, i) {
    d <- matrix(0, nrow = length(data[,1]), ncol = length(data[1,]))
    for (j in 1:ncol(data)) {
      d[,i] <- TTR::runCor(data[,i], data[,j], n = n)
    }
    return(d)
  }

  # call function to loop over iterator i
  worker <- function(i) {
    runcor(data, n, i)
  }

  return(worker)
}

现在在本地计算机上创建一个群集。这允许多个核心单独运行。

parallelcluster <- makeCluster(parallel::detectCores())
models <- parallel::parLapply(parallelcluster, 1:ncol(iris2),
                              wrapper(data = iris2, n = 21))
stopCluster(parallelcluster)

完成后停止并关闭群集。