2017-09-13 51 views
2

我正在寻找一种方法来连接一个结果和一个字符串,其结果是一个平静。其实,如果我使用paste0()quo_name(),我可以做到。但我想知道是否有更优雅的替代方案在我的包中编写函数。这是一个普通的例子:concatenate quosures和字符串

library(dplyr) 

df <- data_frame(
    z_1 = 1, 
    z_2 = 2, 
    y_1 = 10, 
    y_2 = 20 
) 

get_var <- function(.data, var) { 
    xx = enquo(var) 

    select(.data, paste0(quo_name(xx), "_1"), paste0(quo_name(xx), "_2")) 
} 

get_var(df, z) 
# A tibble: 1 x 2 
    z_1 z_2 
    <dbl> <dbl> 
1  1  2 

回答

2

没有的功能,这是它使用dplyr你怎么做:

library(dplyr) 
df %>% 
    select(starts_with("z_")) 

您还可以创建一个功能,在传递一个字符串像这样的变量名:

get_var= function(df, var){ 
    df %>% 
    select(starts_with(paste0(var, "_"))) 
} 

get_var(df, "z") 

现在,棘手部分,当你试图在变量名通过不引用它变成一个功能(将R代码,而不是它包含的值)。这样做的一个办法是在基地R. deparse + substitute这种转换提供给var为一个字符串,这是便于在函数中以后使用符号

get_var = function(df, var){ 
    var_quo = deparse(substitute(var)) 
    df %>% 
    select(starts_with(paste0(var_quo, "_"))) 
} 

最后,这里是如何做enquoquo_name同在rlang/tidyverse包:

library(rlang) 
get_var = function(df, var){ 
    var_quo = quo_name(enquo(var)) 
    df %>% 
    select(starts_with(paste0(var_quo, "_"))) 
} 

get_var(df, z) 
get_var(df, y) 

结果:

# A tibble: 1 x 2 
    z_1 z_2 
    <dbl> <dbl> 
1  1  2 

# A tibble: 1 × 2 
    y_1 y_2 
    <dbl> <dbl> 
1 10 20 

注:

  1. quosures被引述跟踪的环境表现。
  2. enquo采用引用函数参数的符号,引用R代码并将其与函数的环境在一个平静中捆绑在一起。
  3. quo_name将一个定理格式化为一个字符串,该字符串可以在函数中稍后使用。
  4. quo_textquo_name类似,但不检查输入是否是符号。

检查这些:

  1. rlang documentation
  2. Non-Standard Evaluation in R
  3. ?enquo
  4. ?quo_name
+0

如果你可以通过一个变量名到你的选择,我会给予好评。 'starts_with'是我使用的方法 – CPak

+0

@我知道。所以你希望能够传递变量本身,而不是像“z”那样的字符串?例如,'get_var(df,“z”)'不会令人满意吗? – useR

+1

我不是OP顺便说一句。基本上,OP想要定义一个函数,其中数据框和列到选择是作为参数动态传递的。 – CPak