将带逗号的字符串公式传递给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
我正在尝试根据我在预先存在的 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