在多个表达式上使用eval(substitute())

时间:2013-03-20 15:39:00

标签: r eval substitution

我之前问了一个关于How to take in text/character argument without quotes的问题。在我在该问题中提供的场景中,参数的数量是固定的,因此我在函数定义中使用的eval(substitute())的数量对应于我拥有的参数的数量。

现在我有一个场景,我有一个参数,例如factors(见下文),用户可以指定多个列名而不使用它们周围的引号 - 即,他们将使用factor1而不是"factor1"。我想评估用户提供的每个列名。

foo<-function(data.frame, factors){

}

问题1:我想知道当表达式的数量发生变化时,是否有办法将eval(substitute())应用于多个表达式。

正如所指出的,eval(substitute())可能具有潜在的危险性,并且在某些情况下会失败。

问题2:除了使用引用的列名之外,还有一种更优雅的方式来处理问题,如下所示:

foo<-function(data.frame, factors){
   output<-data.frame[, factors]
   output
}
foo(data.frame=dataset, factors=c("factor1", "factor2"))

1 个答案:

答案 0 :(得分:7)

首先,在您提供的示例中,我绝对更喜欢使用引用的列名。对他们有利的一点是,他们将允许有用的间接,如下所示:

XX <- c("cyl", "mpg")
foo(mtcars, XX)

那就是说,如果您确实希望传递一个未加引号的符号向量,这会解决您的问题2

foo <- function(data, factors) {
    jj <- as.character(substitute(factors)[-1])
    data[,jj]
}

head(foo(data = mtcars, factors = c(cyl, mpg)))
#                   cyl  mpg
# Mazda RX4           6 21.0
# Mazda RX4 Wag       6 21.0
# Datsun 710          4 22.8
# Hornet 4 Drive      6 21.4
# Hornet Sportabout   8 18.7
# Valiant             6 18.1