【发布时间】:2021-10-13 03:36:39
【问题描述】:
取如下简单函数:
fun <- function(a, b, c, d, e) {
stopifnot("Input you provide must be equal length." = length(a) == length(b) && length(b) == length(c) && length(c) == length(d) && length(d) == length(e))
result <- (a + b / c + d) / sqrt(e)
result2 <- a/result
return(data.frame(result = result, result2 = result2, a = a, b = b, c = c, d = d, e = e))
}
现在,如果我想映射所有输入值组合的查找表,我可以执行以下操作,例如,使用 purrr 函数:
library(purrr)
df <- expand.grid(a = 1:1000, b = c(1, 2, 3, 4, 5), c = 7, d = 3, e = 5)
out <- pmap_df(d, fun)
但是,即使对于一个较大和一个较小向量的相对简单的情况(在我的应用程序中,这将是最常见的情况),这也很慢。
Unit: seconds
min lq mean median uq max neval
2.235245 2.235245 2.235245 2.235245 2.235245 2.235245 1
如何加快速度,尤其是对于上面概述的简单案例?当然,随着df 越来越大,事情会变慢。
【问题讨论】:
-
pmap_df(d, function(a, b, c, d, e) fun(a = a, b = b, c = c, d = d, e = e))通常写成pmap_df(df, fun)。同样,thereturnfunction call is unnecessary. -
完全同意第一部分。我在脚本中粘贴了一些可以的情况。然而,第二部分非常主观(尽管您提出了一个很好的案例)。仅使用 return 也有很多好的理由(例如,便于非 r-native 共同作者的可读性)。
-
我会告诫不要为非母语“演讲者”“简化”代码。学习语言是无可替代的。当然,代码不应该是“聪明的”,它应该是自我记录和清晰的。但它也应该是惯用的,并发挥其所用语言的优势。
标签: r function performance vectorization