我想用 tidyverse verbs/syntax 编写一个自定义函数,它接受我的函数的分组参数作为字符串

i want to write a custom function with tidyverse verbs/syntax that accepts the grouping parameters of my function as string

我想编写一个函数,其参数为一个数据集、一个要分组的变量和另一个要过滤的参数。我想以这样一种方式编写函数,以便之后可以将 map() 应用于它并将要分组的变量作为向量传递给 map() 。不过,我不知道我的自定义函数 rating() 如何接受要分组为字符串的变量。这是我试过的。

    data = tibble(a = seq.int(1:10), 
                  g1 = c(rep("blue", 3), rep("green", 3), rep("red", 4)), 
                  g2 = c(rep("pink", 2), rep("hotpink", 6), rep("firebrick", 2)),
                  na = NA, 
                  stat=c(23,43,53,2,43,18,54,94,43,87)) 
    
    rating = function(data, by, no){
      data %>%
        select(a, {{by}}, stat) %>%
        group_by({{by}}) %>%
        mutate(rank = rank(stat)) %>%
        ungroup() %>%
        filter(a == no)
    }
    
    fn(data = data, by = g2, no = 5) #this works

这就是我想要使用我的函数的方式


map(.x = c("g1", "g2"), .f = ~rating(data = data, by = .x, no = 1))

...但我得到


Error: Must group by variables found in `.data`.
* Column `.x` is not found.

由于我们正在传递字符元素,因此最好转换为 symbol 并计算 (!!)

library(dplyr)
library(purrr)
rating <- function(data, by, no){
      by <- rlang::ensym(by)
      data %>%
        select(a, !! by, stat) %>%
        group_by(!!by) %>%
        mutate(rank = rank(stat)) %>%
        ungroup() %>%
        filter(a == no)
    }

-测试

> map(.x = c("g1", "g2"), .f = ~rating(data = data, by = !!.x, no = 1))
[[1]]
# A tibble: 1 × 4
      a g1     stat  rank
  <int> <chr> <dbl> <dbl>
1     1 blue     23     1

[[2]]
# A tibble: 1 × 4
      a g2     stat  rank
  <int> <chr> <dbl> <dbl>
1     1 pink     23     1

它也适用于不带引号的输入

> rating(data, by = g2, no = 5)
# A tibble: 1 × 4
      a g2       stat  rank
  <int> <chr>   <dbl> <dbl>
1     5 hotpink    43     3