Search code examples
data.tablerlang

unquote a param upon passing to function using eval(substitute())


Suppose I have a simple function that uses eval(substitue) with an object of class data.table:

f <- function(df,col) eval(substitute(df[,mean(col)]))

If I then have a simple data.table (d), with columns b1 and b2, I can call this function f(), as follows:

d <- data.table(b1 = c(1,2,3), b2 = c(4,5,6))

f(d,b1)
[1] 2

f(d,b2)
[1] 5

However, occasionally, the target column is stored as follows

n <- 1
target <- paste0("b", n)

Obviously, I cannot do f(d,target). I realize that I can do f(d,eval(parse(text = target))). Is there a better option to pass target to the function f(), without changing the current structure/signature of f()?


Solution

  • We can tryCatch and use one of two methods:

    f <- function(df,col) {
      if (tryCatch(is.character(col), error = function(e) FALSE)) {
        col <- as.name(col)
      }
      eval(substitute(df[,mean(col)]))
    }
    f(d, b1)
    # [1] 2
    f(d, "b1")
    # [1] 2
    f(d, b2)
    # [1] 5
    f(d, "b2")
    # [1] 5
    

    Internally, is.character(col) either returns TRUE (as in target) or fails with Error: object 'b1' not found, which is when the tryCatch kicks in.