4

我想将许多(最多 2000+)列分配给data.table; 这个过程给我留下了深刻的印象,因为它非常可并行化,但似乎通过将相同的过程分data.table发给许多工人来处理这个过程并没有得到很好的处理。

我希望以下工作:

library(data.table)
library(parallel)

NN = 100
JJ = 100

cl = makeCluster(2)
DT = data.table(seq_len(NN))
alloc.col(DT, 1.5*JJ)

clusterExport(cl, c("DT", "NN", "JJ"))
clusterEvalQ(cl, library(data.table))

parLapply(cl, seq_len(JJ), function(jj) {
  set(DT, , paste0("V", jj), rnorm(NN))
})

stopCluster(cl)

但是,这会产生一个模糊的错误:

错误checkForRemoteErrors(val):2 个节点产生错误;第一个错误:内部错误,请sessionInfo()向 datatable-help 报告(包括结果):oldtncol (0) < oldncol (1) 但标记了类的 tl。

我想这是由于引用分配的工作原理。分配发生在每个线程上,但这不会DT在全局环境中传回。

有没有办法data.table并行添加列?

4

1 回答 1

1

以下内容适用于 Linux (Ubuntu 16.04)。(注意:mcapply 在 Windows 上不起作用)我有兴趣了解这是否更快

> DT <- do.call("cbind",
               mclapply(seq_len(JJ), function(jj) {
  set(DT, , paste0("V", jj), rnorm(NN))
}, mc.cores = detectCores()))

表现

在 12 核上运行

NN = 100000
JJ = 100

用户系统已用
1.172 2.756 41.707

NN = 100
JJ = 2000

用户系统已过
4.060 11.152 24.101

NN = 1000
JJ = 2000

用户系统已
用 6.580 15.712 139.967

建议

我使用这样的东西来获得 2M 列和 600 行(仍然不是最佳的),希望它符合您的要求

system.time(
  DT2 <- as.data.table(matrix(rnorm(NN*JJ), ncol = JJ))
)
于 2017-02-05T13:10:51.437 回答