【问题标题】:load-balancing in R foreach loopsR foreach 循环中的负载平衡
【发布时间】:2017-03-09 09:01:11
【问题描述】:

有没有办法修改 R foreach 循环如何使用 doParallel 后端进行负载平衡?当并行化执行时间非常不同的任务时,可能会发生所有节点,但一个节点已完成任务,而最后一个节点仍有几项任务要做。这是一个玩具示例:

library(foreach)
library(doParallel)

registerDoParallel(4)

waittime = c(10,1,1,1,10,1,1,1,10,1,1,1,10,1,1,1)

w = iter(waittime)

foreach(i=w) %dopar% {
    message(paste("waiting",i, "on",Sys.getpid()))
    Sys.sleep(i)
}

基本上,代码注册了 4 个内核。对于每个循环i,任务是等待waittime[i] 秒。但是,由于foreach循环中的负载均衡默认情况下似乎是将任务总数拆分为长度为已注册核心数的集合,因此在上面的示例中,第一个核心接收所有带有@的任务987654324@ = 10,而其他 3 个接收具有waittime = 1 的任务,因此这 3 个内核将在第一个完成第一个之前完成所有任务。

有没有办法让foreach() 一次分发一个任务?即在上述情况下,我希望前 4 个任务分布在 4 个核心之间,然后将每个下一个任务分配给下一个可用核心。

谢谢。

【问题讨论】:

    标签: r foreach parallel-processing load-balancing doparallel


    【解决方案1】:

    我自己没有测试过,但是doParallel 后端提供了一个preschedule 选项,类似于mclapply() 中的mc.preschedule 参数。 (参见doParallel vignette 的第 7 节。)

    你可以试试:

    mcoptions <- list(preschedule = FALSE)
    foreach(i = w, .options.multicore = mcoptions)
    

    【讨论】:

      【解决方案2】:

      很抱歉作为答案发布,但我没有足够的代表发表评论。是否可以重写代码以使用 parLapplyLB 或 parSapplyLB?

      parLapplyLB、parSapplyLB 是负载平衡版本,用于将 FUN 应用于 X 的不同元素需要相当多的时间,并且该函数是确定性的或不需要可重现的结果。

      【讨论】:

      • 如果可能的话,我肯定更喜欢使用 foreach。在我的应用程序中,foreach 循环内部的内容比我在示例中放置的两个命令要复杂得多,因此将我的代码转换为单个函数可能会很复杂。还是谢谢。
      • 我猜你是在生产一个非常有限的例子,如果你可以使用 parLapply 以函数的形式在 forloop 中编写你的代码是微不足道的。
      猜你喜欢
      • 2010-12-01
      • 2015-04-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-09-21
      • 2015-08-02
      • 2017-02-05
      • 1970-01-01
      相关资源
      最近更新 更多