接下来是Revolution R的foreach包吗?

Nic*_*ick 16 parallel-processing foreach r next

我查看了大量的文档并完成了大量的Google搜索,但无法找到以下问题的答案:有没有办法在foreach使用该foreach包的并行循环中引入"类似下一个"的功能?

具体来说,我想做一些事情(这不起作用,next但没有):

foreach(i = 1:10, .combine = "c") %dopar% {
    n <- i + floor(runif(1, 0, 9))
    if (n %% 3) {next}
    n
}
Run Code Online (Sandbox Code Playgroud)

我意识到我可以嵌套我的括号,但如果我想在一个长循环中有一些下一个条件,这很快就会变成语法噩梦.

这里有一个简单的解决方法(下一个类似的功能或不同的方法来解决问题)?

Aar*_*ica 12

您可以将代码放在函数中并调用return.从你的例子中不清楚你想要它做什么,n %% 3所以我会回来NA.

funi <- function(i) {
  n <- i + floor(runif(1, 0, 9))
  if (n %% 3) return(NA)
  n
}
foreach(i = 1:10, .combine = "c") %dopar% { funi(i) }
Run Code Online (Sandbox Code Playgroud)


Ste*_*ton 10

虽然看起来很奇怪,但你可以return在foreach循环体中使用a ,而不需要辅助函数(如@Aaron所示):

r <- foreach(i = 1:10, .combine='c') %dopar% {
  n <- i + floor(runif(1, 0, 9))
  if (n %% 3) return(NULL)
  n
}
Run Code Online (Sandbox Code Playgroud)

NULL在此示例中返回A ,因为它被c函数过滤掉,这可能很有用.

此外,尽管它对您的示例不起作用,但该when函数next有时可以取代,并且对于防止计算完全有用:

r <- foreach(i=1:5, .combine='c') %:%
         foreach(j=1:5, .combine='c') %:%
             when (i != j) %dopar% {
                 10 * i + j
             }
Run Code Online (Sandbox Code Playgroud)

内部表达式仅被计算20次,而不是25次.这对于嵌套的foreach循环特别有用,因为when它可以访问所有上游迭代器值.


更新

如果要NULL在列表中返回结果时过滤掉s,则需要编写自己的组合函数.这是一个完整的示例,演示了一个与默认组合函数类似的组合函数,但包含一个过滤机制:

library(doSNOW)
cl <- makeSOCKcluster(3)
registerDoSNOW(cl)

filteredlist <- function(a, ...) {
  values <- list(...)
  c(a, values[! sapply(values, is.null)])
}

r <- foreach(i=1:200, .combine='filteredlist', .init=list(),
             .multicombine=TRUE) %dopar% {
  # filter out odd values of i
  if (i %% 2) return(NULL)
  i
}
Run Code Online (Sandbox Code Playgroud)

请注意,当有超过100个任务结果时,此代码可以正常工作(100是.maxcombine选项的默认值).