Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/r/78.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
将公式列表应用于R data.table_R_Data.table - Fatal编程技术网

将公式列表应用于R data.table

将公式列表应用于R data.table,r,data.table,R,Data.table,我有一个data.table和一个公式列表 DT <- data.table(A = c(1:3), B = c(3:1), C = c(4:6), D = (6:4)) l <- list(f1 = "A + B", f2 = "B + C", f3 = "C - D", f4 = "D / A") 或 是否有一种方法可以使用l中的信息而不使用循环来执行此操作 # some code DT # A B C D f1 f2 f3 f4 # 1: 1 3 4 6

我有一个data.table和一个公式列表

DT <- data.table(A = c(1:3), B = c(3:1), C = c(4:6), D = (6:4))
l <- list(f1 = "A + B", f2 = "B + C", f3 = "C - D", f4 = "D / A")

是否有一种方法可以使用
l
中的信息而不使用循环来执行此操作

# some code
DT
#    A B C D f1 f2 f3       f4
# 1: 1 3 4 6  4  7 -2 6.000000
# 2: 2 2 5 5  4  7  0 2.500000
# 3: 3 1 6 4  4  7  2 1.333333

这太草率了,但您可以使用
调用
解析
粘贴
创建表达式,然后调用该表达式:

library(data.table)
DT <- data.table(A = c(1:3), B = c(3:1), C = c(4:6), D = (6:4))
l <- list(f1 = "A + B", f2 = "B + C", f3 = "C - D", f4 = "D / A")
ncall <- call(":=", names(l), 
          parse(text = paste0("list(", paste(l, collapse = ","), ")")))
DT[ , eval(ncall)]
DT
#    A B C D f1 f2 f3         f4
# 1: 1 3 4 6  4  7 -2 6.00000000
# 2: 2 2 5 5  4  7  0 2.50000000
# 3: 3 1 6 4  4  7  2 1.33333333
库(data.table)

DT如果你是手工构建
l
,那么就这样写吧

L = quote(`:=`(f1 = A + B, f2 = B + C, f3 = C - D, f4 = D / A))
然后你可以像这样使用它

DT[, eval(L)]

#    A B C D f1 f2 f3       f4
# 1: 1 3 4 6  4  7 -2 6.000000
# 2: 2 2 5 5  4  7  0 2.500000
# 3: 3 1 6 4  4  7  2 1.333333
这就是,这解释了

quote()
eval()
类似于其他语言中的宏


这里的循环有什么问题?并不是所有的循环都不好。我只是想知道是否有避免循环的方法……通常,您可以使用
lappy
来避免列上的循环,但正如dayne所说,仅仅使用循环并不总是一件大事。首先,我想应该将它们存储为表达式,而不是文本:
L=lappy(L,函数(x)parse(text=x))
。然后,类似于
DT[,`:=`(name(L),lappy(L,eval.SD))]
的东西,它可以工作,但我不确定是否符合犹太标准。我想按组计算所有这些公式,但data.table不允许我这样做。我该怎么做?提前谢谢你@Nal rA您可能需要发布一个新问题来澄清。当我尝试它时,它对我很有效:
DT[,id:=c(1,1,2)]
然后
DT[,eval(L),by=id][]
谢谢!看来我用错了方法。再次感谢你!你的方法能分组评估所有公式吗?谢谢大家!@Dayne您应该能够添加一个“k”术语并按组计算,例如,
DT[,eval(ncall),by=list(D)
。我还没有明确测试过这一点,这个示例对分组没有意义,但您当然可以自己测试一些代码。
L = quote(`:=`(f1 = A + B, f2 = B + C, f3 = C - D, f4 = D / A))
DT[, eval(L)]

#    A B C D f1 f2 f3       f4
# 1: 1 3 4 6  4  7 -2 6.000000
# 2: 2 2 5 5  4  7  0 2.500000
# 3: 3 1 6 4  4  7  2 1.333333