[.data.table
中的函数set
或表达式:=
意味着data.table通过引用进行更新。我不太了解的是,这种行为与将操作结果重新分配给原始data.frame的方式不同。“通过引用更新”vs浅拷贝
keepcols<-function(DF,cols){
eval.parent(substitute(DF<-DF[,cols,with=FALSE]))
}
keeprows<-function(DF,i){
eval.parent(substitute(DF<-DF[i,]))
}
由于RHS中表达<-
是初始数据帧的浅表副本在最新版本的R,这些功能似乎相当高效。这种基本的R方法与data.table的等价方法有什么不同?差异只与速度或内存使用有关吗?什么时候差异最大?
一些(速度)基准。当数据集只有两个变量时,似乎速度差异可以忽略不计,而且变量越大,速度差异越小。
library(data.table)
# Long dataset
N=1e7; K=100
DT <- data.table(
id1 = sample(sprintf("id%03d",1:K), N, TRUE),
v1 = sample(5, N, TRUE)
)
system.time(DT[,a_inplace:=mean(v1)])
user system elapsed
0.060 0.013 0.077
system.time(DT[,a_inplace:=NULL])
user system elapsed
0.044 0.010 0.060
system.time(DT <- DT[,c(.SD,a_usual=mean(v1)),.SDcols=names(DT)])
user system elapsed
0.132 0.025 0.161
system.time(DT <- DT[,list(id1,v1)])
user system elapsed
0.124 0.026 0.153
# Wide dataset
N=1e7; K=100
DT <- data.table(
id1 = sample(sprintf("id%03d",1:K), N, TRUE),
id2 = sample(sprintf("id%03d",1:K), N, TRUE),
id3 = sample(sprintf("id%010d",1:(N/K)), N, TRUE),
v1 = sample(5, N, TRUE),
v2 = sample(1e6, N, TRUE),
v3 = sample(round(runif(100,max=100),4), N, TRUE)
)
system.time(DT[,a_inplace:=mean(v1)])
user system elapsed
0.057 0.014 0.089
system.time(DT[,a_inplace:=NULL])
user system elapsed
0.038 0.009 0.061
system.time(DT <- DT[,c(.SD,a_usual=mean(v1)),.SDcols=names(DT)])
user system elapsed
2.483 0.146 2.602
system.time(DT <- DT[,list(id1,id2,id3,v1,v2,v3)])
user system elapsed
1.143 0.088 1.220
现在我明白了setkey
或X[Y,:=
]不能浅拷贝的期限来表示 - 所以我真的只是要求有关创建/删除新的列或行我。