arrange()不识别列名参数

时间:2017-11-01 13:32:11

标签: r dplyr

在R中,我使用dplyr,更具体地说arrange()。 不知怎的,arrange函数没有按预期工作。

在下面的示例中,我首先存储列的名称,然后将此变量作为参数传递给名为' my_function'的自定义函数。

target_column = 'mean_age'

# below the function
my_function <- function(target_column, number){
    df <- read.csv('file.csv', stringsAsFactors=FALSE)
    df <- df[, c(1,4,10)]
    names(df) <-  c('place','state','mean_age')
    df1 <- df %>% group_by(state) %>% arrange(target_column) 
    df1 %>% summarise(rank = nth(target_column, number))        
}
当&#39; my_function&#39;时,

R会返回错误由于arrange()输入而被调用:

  

&#34; arrange_impl(.data,dots)出错:     位置1的大小不正确(1),期望:4000&#34;

当列的名称直接放入arrange()时,而不是引用字符串的变量(如上例所示),它接受参数。

df %>% group_by(state) %>% arrange(mean_age) 

如何以更好的方式传递列名称的参数到“my_function&#39;”,以便arrange()能够识别它?

2 个答案:

答案 0 :(得分:4)

您需要首先将字符串参数解析为quosure,然后用!!取消引用它:

library(dplyr)
library(rlang)

target_column = 'mean_age'

my_function <- function(target_column, number){
    target_quo = parse_quosure(target_column)

    df <- read.csv('file.csv', stringsAsFactors=FALSE)
    df <- df[, c(1,4,10)]
    names(df) <-  c('place','state','mean_age')
    df1 <- df %>% group_by(state) %>% arrange(!!target_quo) 
    df1 %>% summarise(rank = nth(target_column, number))        
}

my_function('mean_age', 10)

如果您希望能够将target_column作为未加引号的列名提供,则可以改为使用enquo

my_function <- function(target_column, number){
    target_quo = enquo(target_column)

    df <- read.csv('file.csv', stringsAsFactors=FALSE)
    df <- df[, c(1,4,10)]
    names(df) <-  c('place','state','mean_age')
    df1 <- df %>% group_by(state) %>% arrange(!!target_quo) 
    df1 %>% summarise(rank = nth(target_column, number))        
}

my_function(mean_age, 10)

注意:

通常,enquo也适用于字符串参数,但arrange本身不允许,因此以下内容不适用于第二个示例:

my_function('mean_age', 10)

下面是一个玩具示例来说明我的意思,因为OP的问题不可重复:

library(dplyr)
library(rlang)

test_func = function(var){
    var_quo = parse_quosure(var)
    mtcars %>%
      select(!!var_quo) %>%
      arrange(!!var_quo)
}

test_func2 = function(var){
  var_quo = enquo(var)
  mtcars %>%
    select(!!var_quo) %>%
    arrange(!!var_quo)
}

<强>结果:

> test_func("mpg") %>%
+   head()
   mpg
1 10.4
2 10.4
3 13.3
4 14.3
5 14.7
6 15.0

> test_func2(mpg) %>%
+   head()
   mpg
1 10.4
2 10.4
3 13.3
4 14.3
5 14.7
6 15.0

> test_func2("mpg") %>%
+   head()
  

arrange_impl(.data,dots)出错:     位置1的大小不正确(1),期望:32

答案 1 :(得分:0)

必须更新@avid_useR的良好答案,因为现在不推荐使用'rlang :: parse_quosure'。

要简短回答该问题,如何使'dplyr :: arrange'接受字符串或包含要对列名称进行排序的字符串的变量,可以执行以下操作:

target_column = rlang::sym('mean_age')
df %>% group_by(state) %>% arrange(!!target_column)

或作为单线(如果只需要使用一次):

df %>% group_by(state) %>% arrange(!! rlang::sym(target_column))