当管道操作符%>%
与dplyr
,ggvis
,dycharts
等包一起使用时,如何有条件地执行一个步骤?例如:
step_1 %>%
step_2 %>%
if(condition)
step_3
这些方法似乎并不奏效:
step_1 %>%
step_2
if(condition) %>% step_3
step_1 %>%
step_2 %>%
if(condition) step_3
还有很长的路要走:
if(condition)
{
step_1 %>%
step_2
}else{
step_1 %>%
step_2 %>%
step_3
}
有没有一个更好的方法,没有所有的冗余?
6条答案
按热度按时间bmvo0sr51#
下面是一个利用
.
和ifelse
的快速示例:在
ifelse
中,如果Y
是TRUE
,if将加1,否则它将返回X
的最后一个值,.
是一个替代函数,它告诉函数上一步的输出到哪里,所以我可以在两个分支上使用它。编辑正如@BenBolker指出的,您可能不想要
ifelse
,所以这里有一个if
版本。感谢@Frank指出我应该在
if
和ifelse
语句周围使用{
大括号来继续这个链。afdcj2ne2#
我想
purrr::when()
就是这样的情况,如果几个数的和小于25,我们就求和,否则返回0。when
返回第一个有效条件的操作结果。将条件放在~
的左边,将操作放在它的右边。在上面,我们只使用了一个条件(然后使用了else case),但您可以有许多条件。您可以轻松地将其集成到更长的管道中。
wfypjpf43#
下面是@JohnPaul给出的答案的一个变体。这个变体使用
if
函数而不是复合if ... else ...
语句。请注意,在这种情况下,
if
函数前后和ifelse
函数前后都不需要花括号,只需在if ... else ...
语句前后使用。但是,如果点占位符仅出现在嵌套函数调用中,那么magrittr将默认地把左手边的参数输入到右手边的第一个参数中。将表达式括在大括号中可以覆盖此行为。请注意这两个链之间的区别:点占位符在
if
函数中出现的两次都嵌套在函数调用中,因为. + 1
和. + 2
分别被解释为+`(., 1)`和
+(., 2)
。因此,第一个表达式返回if`(1, TRUE, 1 + 1, 1 + 2)`的结果。(奇怪的是,
if并不抱怨额外的未使用参数),第二个表达式返回
if(TRUE, 1 + 1, 1 + 2)
的结果,这是本例中所需的行为。有关magrittr管道操作符如何处理点占位符的详细信息,请参见
%>%
的help file,特别是“将点用于次要用途”一节。vuktfyat4#
对我来说,最简单的方法是稍微远离管道(尽管我对其他解决方案很感兴趣),例如:
这是对@JohnPaul的答案的一个小小的修改(您可能并不真的需要
ifelse
,它会计算它的两个参数并被向量化)。如果修改它以在条件为false时自动返回.
,那就太好了......(* 注意 *:我认为这是可行的,但还没有真正测试/考虑太多...)o7jaxewo5#
我喜欢
purrr::when
,这里提供的其他基本解决方案都很棒,但我想要更紧凑和灵活的东西,所以我设计了函数pif
(管道if),请参见答案末尾的代码和文档。参数可以是函数的表达式(支持公式表示法),如果condition为
FALSE
,默认返回输入不变。用于其他答案中的示例:
其他例子:
功能
kkbh8khc6#
一种可能的解决方案是使用匿名函数