将带逗号的字符串公式传递给R数据table

Pass character string formula with comma to R data table

我正在尝试根据我在预先存在的 data.frame 中的公式将新变量分配给 data.table,方法是循环遍历 data.frame,如下所示:

# Setup
DT <- data.table(id = c("a", "b"), value1 = c(1, 3), value2 = c(2,4))
var_exp = data.frame(varname = c("ratio", "sum"), 
                     expr = c("(value1 / value2) * 100", 
                              'rowSums(.SD, na.rm=TRUE), .SDcols=c("value1", "value2")'),
                     stringsAsFactors=FALSE)

# Assign new variables
for (row in 1:nrow(var_exp)) {
  varname <- var_exp[row, "varname"]
  expr <- var_exp[row, "expr"]
  
  DT[, (varname) := eval(parse(text = expr))]
}

第一个表达式理解没有问题。但是,第二个表达式 returns 出错,因为表达式中有一个逗号:

Error in parse(text = expr) : <text>:1:29: unexpected ','
1: lapply(.SD, sum, na.rm=TRUE),

如何将此表达式传递给 data.table

通常将字符串作为代码求值不是一个好的做法,但这里有一种方法可以做到这一点。

library(data.table)

for (row in 1:nrow(var_exp)) {
  varname <- var_exp[row, "varname"]
  expr <- var_exp[row, "expr"]
  eval(parse(text = sprintf('DT[, %s := %s]', varname, expr)))
}

DT

#   id value1 value2 ratio sum
#1:  a      1      2    50   3
#2:  b      3      4    75   7

我们可以用 lapply

DT[, (var_exp$varname) := setDT(var_exp)[, lapply(sprintf("DT[,%s]",
       expr), function(x) eval(parse(text = x)))]]
DT
   id value1 value2 ratio sum
1:  a      1      2    50   3
2:  b      3      4    75   7