以编程方式在 dplyr::top_n 中设置列​​名

Programmatically setting a column name in dplyr::top_n

我想以编程方式为 dplyr::top_n 函数设置列名。

getSubset <- function(df, t, f) {
  df %>%
    top_n(t, wt = eval(as.name(f), envir = df))
}

data.frame(x = 1:20, y = 20:1) %>%
  getSubset(10, "x")

它告诉我 Error: object 'f' not found。我试着玩 lazyeval 包,但不知何故我一直误解这个概念。有人能把我推向正确的方向吗?谢谢!

您的问题是 top_n 使用了非标准评估。它试图在数据框 df 的上下文中计算表达式 eval(as.name(f), envir = df)),而 f 在该环境中不存在。

一种解决方法是暂时将 wt 的所需值添加到数据框。

getSubset <- function(df, t, f) {
    df %>%
        mutate(.wt = eval(as.name(f), envir = df)) %>% 
        top_n(t, wt = .wt) %>% 
        select(-.wt)
}

data.frame(x = 1:20, y = 20:1) %>%
    getSubset(10, "x")

另一种方法是使用 lazyeval 包中的 interp

getSubset <- function(df, t, f) {
    call <- quote(df %>%
                      top_n(t, wt = .wt))
    call <- interp(call, .wt = eval(as.name(f), envir = df))
    eval(call)
}

data.frame(x = 1:20, y = 20:1) %>%
    getSubset(10, "x")