包含foreach的R包将使用doParallel而不是doMPI,找不到对象

时间:2017-09-05 20:54:50

标签: r foreach parallel-processing doparallel dompi

我正在尝试在foreach语句和doMPI后端中编写一个包含多个嵌套函数的R包。它抛出一个“无法找到”XXX“对象错误。奇怪的是,如果我使用doParallel作为后端,则不会发生此错误。这是问题的一个例子,但我可以使用一个有效的解决方案,doMPI很多更大的问题。

这是使用RStudio,roxygen,devtools等编译到R-Package中的代码。

#' Test function level 1
#' @param var11 first variable for function 1
#' @param var12 second variable for function 1
#' @param var13 third variable for function 1
#' @export fun1

fun1 <- function (fun2.params, fun3.params, var11, var12, var13, ...) {

    results <- data.frame (foreach::`%dopar%`(
               foreach::`%:%`(foreach::foreach(j = 1:var11, .combine = cbind),
               foreach::foreach (i = 1:var12, .combine=rbind)),
               {
                   out3 <- replicate(var13,
                                     do.call(fun2,
                                             c(list(fun3.params=fun3.params),
                                               fun2.params)))
                   output2 <- data.frame(mean(out3))
        }
    )
)
    ## save outputs for subsequent analyses if required
saveRDS(results, file = paste("./outputs/", var13 ,"_", var12, "_", var11, "_",
                              format(Sys.time(), "%d_%m_%Y"), ".rds", sep=""))
}

#' Test function level 2
#' @param var21 first variable for function 2
#' @param var22 second variable for function 2
#' @export fun2

fun2 <- function (fun3.params, var21, var22, ...) {
    out2 <- `if` (rpois(1, var21) > 0, var22 * do.call(fun3, fun3.params), 0)
}

#' Test function level 3
#' @param var31 first variable for function 3
#' @param var32 second variable for function 3
#' @param var33 third variable for function 3
#' @export fun3

fun3 <- function (var31, var32, var33, ...) {
    out3 <- var31 * rnorm(1, mean=var32, sd= var33)
}

然后我加载库并使用emacs ESS(或从RStudio编辑器)和这些命令从.R文件调用顶级函数

library(toymod)
library(doParallel)
cl <-makeCluster(10)
registerDoParallel(cl)

fun1.params <- list(var11=10, var12=150, var13=365)
fun2.params <- list(var21=0.05,var22=9.876)
fun3.params <- list(var31=1.396,var32=14.387,var33=3.219)

do.call(fun1, c(list(fun2.params = fun2.params,
                     fun3.params = fun3.params),
                fun1.params))

当我使用doParallel作为并行后端运行它时工作正常,但是当我使用doMPI运行它时,我收到以下错误

Error in { : task 12 failed - "object 'fun2' not found"

这是在Ubuntu 16.04 Linux上运行,使用R 3.4.1,doMPI 0.2.2和doParallel。我把整个包放在https://github.com/jamaas/toymod.git

的github上

有人可以告诉我是否需要更改doMPI的代码?这似乎与生产R包有关。

1 个答案:

答案 0 :(得分:1)

我认为问题是您需要使用foreach .packages='toymod'选项。这是因为foreach循环的主体实际上并不是“玩具模式”的一部分。包,因此您需要加载&#39; toymod&#39;就像你要从任何其他R包中访问函数一样。

我不知道为什么在使用doParallel时这不是必需的。我想doParallel必须自动加载foreach循环所在的包。我将更多地研究这个,并且可能修改doMPI来做同样的事情。