首页 > 解决方案 > 将字符串传递给 R 函数并将其用作函数中的列名

问题描述

我有一个数据框,其中包含几个科目的学生分数列表(每个科目由一列表示)我想为每个科目(数学、科学和阅读)进行下面的计算

avgdata_math <- data%>% 
   group_by(country) %>% 
   summarise(ci = list(bootstrap_ci(sex, Math, weight))) %>% 
   unnest_wider(ci) %>% 
   ungroup() %>% 
   mutate(country = fct_reorder(country, avg))

由于我必须重复两次相同的代码,我想编写一个函数来进行计算(不旋转数据框)

aus_nz <- function(df, subject = "Math") {
   df %>%
    group_by(country) %>% 
    summarise(ci = list(bootstrap_ci(sex, subject, weight))) %>% 
    unnest_wider(ci) %>% 
    ungroup() %>% 
    mutate(country = fct_reorder(country, avg))
}

这给了我一个错误,因为我已经将列名(主题)作为字符串传递,然后对数据进行分组,然后在调用 bootstrap_ci 函数时使用字符串值,而它应该是在那里传递的一列数据(应该是分组操作后)。

标签: rfunctiondplyrtidyeval

解决方案


!! rlang::ensym(subject)在您的函数中使用应该可以。

aus_nz <- function(df, subject = "Math") {
   df %>%
    group_by(country) %>% 
    summarise(ci = list(bootstrap_ci(sex, !! rlang::ensym(subject), weight))) %>% 
    unnest_wider(ci) %>% 
    ungroup() %>% 
    mutate(country = fct_reorder(country, avg))
}

更新

如果您还想将分组变量作为字符串传递给函数,并且有时您想要分组的变量不止一个,那么使用!!!,rlang::ensyms()和 ellipsis...参数可以解决问题,如果不是最后一行你的功能。fct_reorder只需要一个变量。如果有两个分组变量:你会怎么做?创建两个新变量并按avg?对每个分组变量重新排序 查看您的数据(可能使用 )也会有所帮助dput(head(...))

aus_nz <- function(df, subject = "Math", ...) {

group_var <- rlang::ensyms(...)

  df %>%
    group_by(!!! group_var) %>%
    summarise(ci = list(bootstrap_ci(sex, !! rlang::ensym(subject), weight))) %>%
    unnest_wider(ci) %>%
    ungroup() # %>% last line needs to be fixed
    # mutate(grouped_by = fct_reorder(!!! group_var, avg))
} 

如果您不想使用 ellipsis 参数,您可以使用rlang::symsand 一个字符向量(具有一个或多个元素)来代替:

aus_nz <- function(df, subject = "Math", group = "country") {

group_var <- rlang::syms(group)

  df %>%
    group_by(!!! group_var) %>%
    summarise(ci = list(bootstrap_ci(sex, !! rlang::ensym(subject), weight))) %>%
    unnest_wider(ci) %>%
    ungroup() # %>% last line needs to be fixed
    # mutate(grouped_by = fct_reorder(!!! group_var, avg))
} 

推荐阅读