如何在没有更大代码重做的情况下并行运行多个独立且不相关的函数?

时间:2017-05-16 15:12:50

标签: r parallel-processing

我一直在互联网上搜索,试图理解并行处理。

他们似乎都假设我有某种循环功能,例如数据集的每第N行在N个核心之间划分并在之后合并,并且我指向了许多并行化的apply()函数。

(警告,下面的丑陋代码)

我的情况虽然是我的表格

tempJob <- myFunction(filepath, string.arg1, string.arg2)

其中path是文件位置,字符串参数是各种排序数据的方法。

我目前的工作流程只是积累了很多

tempjob1 <- myFunction(args)
tempjob2 <- myFunction(other args)
...
tempjobN <- myFunction(some other args here)

# Make a list of all temporary outputs in the global environment
temp.list <- lapply(ls(pattern = "temp"), get)

# Stack them all
df <- rbindlist(temp.list)

# Remove all variables from workspace matching "temp"
rm(list=ls(pattern="temp"))

这些工作是完全独立的,原则上可以在8个独立的R实例中运行(尽管我觉得这样做很麻烦)。如何将前8个作业分成8个核心,每当核心完成其工作并将处理过的数据集返回到全局环境时,它只需要接下来的任何一个作业。

3 个答案:

答案 0 :(得分:3)

使用future软件包(我是作者),您可以通过对代码进行细微修改来实现您的目标 - 使用“未来”作业%<-%而不是常规作业{{1}对于想要异步运行的代码。

<-

答案 1 :(得分:1)

除非您不幸使用Windows,否则您可以尝试使用 GNU Parallel

parallel Rscript ::: script1.R script2.R JOB86*.R

如果你的CPU有8个内核,这将保持一次运行8个脚本。如果您一次只想要4个,则可以使用-j 4进行更改。 JOB86部分只是随机的 - 我做了。

您还可以为进度条添加开关,如何处理错误,添加参数以及在多台计算机上分配作业。

如果您使用的是Mac,则可以使用自制程序安装 GNU Parallel

brew install parallel

答案 2 :(得分:0)

我认为最简单的方法是使用其中一个并行apply函数。那些将完成分离工作的所有繁琐工作,承担下一个工作的任何工作,等等。

将所有参数放入列表中:

args <- list(
    list(filePath1, stringArgs11, stringArgs21),
    list(filePath2, stringArgs12, stringArgs22),
    ...
    list(filePath8, stringArgs18, stringArgs28)
)

然后执行类似

的操作
library(parallel)
cl <- makeCluster(detectCores())
df <- parSapply(cl, args, myFunction)

我对parSapply不确定,而且我无法检查R因为刚才在我的机器上工作。如果这不起作用,请使用parLapply,然后操纵结果。