r - 为什么这个并行计算代码只使用了 1 个 CPU?

标签 r doparallel parallel-foreach

我正在使用 foreachparallel库来执行并行计算,但出于某种原因,在运行时,它一次只使用 1 个 CPU(我使用“top”(Linux 终端上的 Bash)查找它)。

服务器有 48 个内核,我尝试过:

  • 使用 24、12 或 5 核
  • 示例代码(如下)
  • 在 Windows 中,此类任务出现,但它们不使用任何 CPU
  • list.of.packages <- c("foreach", "doParallel")
    new.packages <- list.of.packages[!(list.of.packages %in% installed.packages()[,"Package"])]
    if (length(new.packages)) install.packages(new.packages)
    
    library(foreach)
    library(doParallel)
    
    no_cores <- detectCores() / 2 # 24 cores
    cl<-makeCluster(no_cores)
    registerDoParallel(cl)
    
    df.a = data.frame(str = cbind(paste('name',seq(1:60000))), int = rnorm(60000))
    df.b = data.frame(str = sample(df.a[, 1]))
    df.b$int = NA
    
    foreach(row.a = 1:length(df.a$str),
            .combine = rbind,
            .verbose = T)  %dopar% {
              row.b = grep(pattern = df.a$str[row.a], x = df.b$str)
              df.b$int[row.b] = df.a$int[row.a]
              df.b
            }
    stopCluster(cl)
    
    

    我希望这段代码使用多个 CPU(与定义的一样多),但它实际上使用了 1 个。

    最佳答案

    运行 foreach(..., verbose = TRUE)了解正在发生的事情。稍微更改了正在运行的代码,以便更好地识别并行代码何时运行。

    library(foreach)
    library(doParallel)
    
    no_cores <- detectCores() / 2 # 24 cores
    cl<-makeCluster(no_cores)
    registerDoParallel(cl)
    
    base = 2
    
    out <- foreach(exponent = 2:400,
            .combine = sum, .verbose = TRUE)  %dopar%
      runif(1000000)
    

    第一段:
    # discovered package(s):  
    # no variables are automatically exported
    # explicitly exporting package(s):
    # numValues: 3999, numResults: 0, stopped: TRUE
    

    这个设置不是平行的——这是你的主人设置你的 child 。这需要很长时间才能使用 2:40000000 ,这可能是您停止的地方,并且您只会看到一个内核正在使用中。
    # numValues: 79, numResults: 0, stopped: TRUE
    # got results for task n
    

    等待打印时的计算应该是并行的。在 Windows 上,我看到 4 个内核正在计算每个 runif .
    # calling combine function
    # evaluating call object to combine results:
    #   fun(accum, result.n)
    

    这对每个具有不同 n 值的 worker 运行。这是您的组合功能,也不是并行的。

    我认为您的代码已卡在设置部分上,而您只是在观察操作的串行部分。如果没有,我会看 verbose = TRUE 发生了什么并留意更多线索。

    我不知道您的主要问题是如何设置的,但是您的示例并不是如何设置并行化的好示例 - 您正在使用数百万个工作人员来执行非常小的任务,因此每个工作人员的串行开销成本非常高。如果您可以向每个工作人员发送更大的块,您将看到性能提高。

    关于r - 为什么这个并行计算代码只使用了 1 个 CPU?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57477054/

    相关文章:

    Rcpp 找不到 Rtools : "Error 1 occurred building shared library"

    r - 我看到了,但我不相信。 R 中的合法名称、管道操作和点

    r - 使用 doparallel 在 foreach 循环内循环

    R foreach : Read and manipulate multiple files in parallel

    r - foreach、doParallel 和随机生成

    r - R : how to use the cores 中的并行计算

    r - 如何更改 ggplot2 R 中 stat_poly_eq 的字体大小

    r - data.table 列子集返回 0 行

    r - 在 R 中执行详尽搜索的最快方法是什么

    具有异步任务和相关后异步任务的 C# ForEach 循环