我发现使用future
(and furrr
) 包进行并行化的速度增益R
并不令人满意。尤其是速度提升并不接近线性。我的机器有 4 个工人,所以我认为当我指定的工人数量不大于我机器中可用的核心数量时,速度增益应该是线性的。然而,事实并非如此。
下面是一个说明问题的例子,我画了 10^7 个随机数 500 次。
library(future)
library(furrr)
# Parameters
n <- 1e7
m <- 500
# Compute the mean
rmean <- function(x, n) {
rand.vec <- runif(n)
rand.mean <- mean(rand.vec)
return(rand.mean)
}
# Record the time used to compute the mean of n numbers for m times
rtime <- function(m, n) {
t1 <- Sys.time()
temp <- future_map(.x = 1:m,
.f = rmean,
n = n,
.options = furrr::furrr_options(seed = TRUE))
t2 <- Sys.time()
# Print the time used
print(t2 - t1)
return(temp)
}
# Print the time used for different number of workers
plan(multisession, workers = 1)
set.seed(1)
x <- rtime(m, n)
# Time difference of 2.503885 mins
plan(multisession, workers = 2)
set.seed(1)
x <- rtime(m, n)
# Time difference of 1.341357 mins
plan(multisession, workers = 3)
set.seed(1)
x <- rtime(m, n)
# Time difference of 57.25641 secs
plan(multisession, workers = 4)
set.seed(1)
x <- rtime(m, n)
# Time difference of 47.31929 secs
在上面的例子中,我得到的速度增益是:
- 2 名工人 1.87 倍
- 3 名工人的 2.62 倍
- 4 名工人的 3.17 倍
上例中的速度增益并不接近线性,尤其是当我使用 4 个工人时。我认为这可能是因为plan
函数的开销时间。但是,如果我在设置工人数量后多次运行该过程,则速度增益是相似的。这说明如下:
plan(multisession, workers = 3)
set.seed(1)
x <- rtime(m, n)
# Time difference of 58.07243 secs
set.seed(1)
x <- rtime(m, n)
# Time difference of 1.012799 mins
set.seed(1)
x <- rtime(m, n)
# Time difference of 57.96777 secs
我还尝试使用包中的future_lapply
函数future.apply
而不是包中的future_map
函数furrr
。但是,它们的速度增益也相似。因此,我将不胜感激任何关于这里发生的事情的建议。谢谢!