R - 加速数组维度上的循环

标签 r performance for-loop multidimensional-array

我正在处理一个具有维度的数组

[1] 290 259  55   4

对于最后三个维度的每次重复,我想对第一个维度的 290 个元素执行滚动均值,将元素数量减少到 289 个。最后,我需要创建一个包含更新值的数据框。

下面的代码实现了我所需要的,但是需要很长时间才能运行(实际上,我必须在结束之前中断它)。
library(zoo)

# Generate random data with same dimensions as mine
my.array <- array(1:16524200, dim=c(290,259,55,4))

# Get dimension sizes
dim2 <- dim(my.array)[2]
dim3 <- dim(my.array)[3]
dim4 <- dim(my.array)[4]

# Pre-allocate data frame to be used within the loop
df2 <- data.frame()

# Loop over dimensions
for (i in 1:dim4) {
  for (j in 1:dim3) {
    for (k in 1:dim2) {

      # Take rolling average
      u <- rollapply(my.array[,k,j,i], 2, mean)

      # Assemble data frame
      df1 <- data.frame(time=i, level=j, lat=k, wind=u)
      df2 <- rbind(df2, df1)

    }
  }
}
# Very slow, and uses only one machine core

我觉得可以通过使用向量化甚至某种并行来改善这段代码的处理时间,但我不知道如何。

有什么建议可以使此代码更有效吗?

最佳答案

apply()适用于任意数量的维度,因此您可以使用包裹在 as.data.frame.table() 中的以下内容更快地获得相同的结果有效地将输出从数组转换为数据帧:

library(zoo)
df <- as.data.frame.table(apply(my.array, c(2,3,4), rollmean, 2))

并非绝对必要,但这可以整理以匹配您的原始输出:
idx <- sapply(df, is.factor)
df[idx] <- sapply(df[idx], as.integer)

df <- setNames(df[c(4,3,2,5)], c("time", "level", "lat", "wind"))

检查结果是否相同:
identical(df2, df)
[1] TRUE

关于R - 加速数组维度上的循环,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59419062/

相关文章:

regex - 从R中的url路径获取文件名

r - R 中 match 和 lapply 的组合

r - 分块循环遍历列表

java - .NET与Java子串操作性能对比

performance - 在 Elasticsearch 中使用 function_score 时,过滤器是在 function_score 对象内部还是外部有关系吗?

python - python中嵌入式循环的多线程

r - 动态公式不适用于startsWith和colnames

MySQL 的 Join 函数?这可以改进吗?

python - Python 中的 For 循环执行

javascript - React-Native 中更快的数组循环