问题描述
我曾经使用 mutate _ 和.dots参数,使用用户提供的变量(字符串格式)和函数内部计算的变量(如b)的组合来评估函数内部的一组公式下面的变量):
require(dplyr)
f <- function(data,a)
{
b <- "Sepal.Length"
mutate_call <- list(new_1 = lazyeval::interp( ~ a*10,a=as.name(a)),new_2 = lazyeval::interp( ~ b*10,b=as.name(b)) )
data %>%
as_tibble() %>%
mutate_(.dots = mutate_call) %>%
head() %>%
print()
}
f(iris,"Sepal.Width")
但是,当过渡到最新的dplyr版本时,这将不再可能(除非我继续使用不推荐使用的版本mutate_)。如何使用 mutate 代替 mutate _ 获得与 f 相同的结果?
如果我继续使用公式,会容易得多。
解决方法
我的建议是从公式切换到表达式,然后将unquote-splice运算符!!!
与常规mutate()
一起使用:
f <- function(data,a)
{
# Convert strings to symbols
a <- as.name(a)
b <- as.name("Sepal.Length")
# Use rlang::exprs to define the expressions
# Use !! to replace a and b with the symbols stored inside them
mutate_call <- rlang::exprs(new_1 = !!a*10,new_2 = !!b*10)
data %>%
as_tibble() %>%
mutate(!!!mutate_call) %>% # <-- !!! effectively "pastes" the expressions
head() %>%
print()
}
f(iris,"Sepal.Width")
# # A tibble: 6 x 7
# Sepal.Length Sepal.Width Petal.Length Petal.Width Species new_1 new_2
# <dbl> <dbl> <dbl> <dbl> <fct> <dbl> <dbl>
# 1 5.1 3.5 1.4 0.2 setosa 35 51
# 2 4.9 3 1.4 0.2 setosa 30 49
# 3 4.7 3.2 1.3 0.2 setosa 32 47
# 4 4.6 3.1 1.5 0.2 setosa 31 46