【发布时间】:2021-08-24 08:11:22
【问题描述】:
自 R 版本 4.1.0 以来,管道 |> 处于稳定版本中。当将 lhs 传递给除第一个参数之外的参数时,手册的示例显示:
mtcars |> subset(cyl == 4) |> (function(d) lm(mpg ~ disp, data = d))()
或者当使用\(x)时
mtcars |> subset(cyl == 4) |> (\(d) lm(mpg ~ disp, data = d))()
或者使用当前需要激活的PIPEBIND:
Sys.setenv(`_R_USE_PIPEBIND_` = TRUE)
mtcars |> subset(cyl == 4) |> . => lm(mpg ~ disp, data = .)
除了|>,Bizarro pipe ->.; 也可以像这样使用
mtcars |> subset(cyl == 4) ->.; lm(mpg ~ disp, data = .)
R 中管道符号的一个目的是允许以一种可以使处理步骤序列的方式编写嵌套的调用序列 更容易遵循 ,至少对我来说,这也是->.;实现的。 Bizarro 管道并不是真正的管道,但对我来说,它目前是|> 的一个受欢迎的替代品,尤其是在将 lhs 传递给第一个以外的参数的情况下。但是在使用它时,我得到comments 不使用它。
所以我想知道 Bizarro 管子是否有缺点建议不要使用它?
到目前为止,我看到它在环境中创建或覆盖了.,并且
保留此引用,这将在修改时强制复制。但是当调用一个函数时,参数中有数据,也会创建对该数据的引用。而当使用for 循环时,var 在使用后仍然存在。
for(i in iris) {}
tracemem(i) == tracemem(iris[[ncol(iris)]])
#[1] TRUE
在性能方面也没有太大的劣势:
x <- 42
library(magrittr)
Sys.setenv(`_R_USE_PIPEBIND_` = TRUE)
#Nonsense operation to test Performance
bench::mark(x
, identity(x)
, "x |> identity()" = x |> identity()
, "x |> (\\(y) identity(y))()" = x |> (\(y) identity(y))()
, "x |> . => identity(.)" = x |> . => identity(.)
, "x ->.; identity(.)" = {x ->.; identity(.)}
, x %>% identity
)
# expression min median `itr/sec` mem_alloc `gc/sec` n_itr
# <bch:expr> <bch:tm> <bch:tm> <dbl> <bch:byt> <dbl> <int>
#1 x 60.07ns 69.03ns 13997474. 0B 0 10000
#2 identity(x) 486.96ns 541.91ns 1751206. 0B 175. 9999
#3 x |> identity() 481.03ns 528.06ns 1812935. 0B 0 10000
#4 x |> (\(y) identity(y))() 982.08ns 1.08µs 854349. 0B 85.4 9999
#5 x |> . => identity(.) 484.06ns 528.06ns 1815336. 0B 0 10000
#6 x ->.; identity(.) 711.07ns 767.99ns 1238658. 0B 124. 9999
#7 x %>% identity 2.86µs 3.23µs 294945. 0B 59.0 9998
【问题讨论】:
-
这个问题似乎特别关注性能。正如我在回答中解释的那样,性能不是问题。我有点困惑,你会立即想到这一点。
-
也可以写成:
mtcars |> subset(cyl == 4) |> lm(formula = mpg ~ disp)。我认为性能是重点的原因是它似乎是 |> 背后的主要激励因素,它放弃了 %>% 和 bizarro 管道的大部分功能,以便通过语法转换来实现它。我怀疑关于 bizarro 管道的副作用论点是否真的具有实际意义。 -
@G.Grothendieck 是的,当占位符之前的所有参数都被填满时,可以避免使用占位符。但有时这会以大量的文字告终。
-
@G.Grothendieck 我希望让人们相信这是具有实际重要性:故意编写比可能的更健壮的代码只是一个难以置信 坏主意:记住“one in a million is next Tuesday” 的软件工程格言:由于规模的原因,听起来不太可能的错误总是导致问题。并且应始终将隐藏错误以静默方式产生错误结果的可能性降至最低。
标签: r