R data.table中dlply的等效值
我试图实现dlply对R data.table中dlply的等效值,r,data.table,R,Data.table,我试图实现dlply对data.table的相同功能。作为一个非常简单的例子: library(plyr) library(data.table) dt <- data.table( p = c("A", "B"), q = 1:2 ) dlply( dt, "p", identity ) $A p q 1 A 1 $B p q 1 B 2 dt[ , identity(.SD), by = p ] p q 1: A 1 2: B 2 foo <- functi
data.table
的相同功能。作为一个非常简单的例子:
library(plyr)
library(data.table)
dt <- data.table( p = c("A", "B"), q = 1:2 )
dlply( dt, "p", identity )
$A
p q
1 A 1
$B
p q
1 B 2
dt[ , identity(.SD), by = p ]
p q
1: A 1
2: B 2
foo <- function(x) as.list(x)
dt[ , foo(.SD), by = p ]
p q
1: A 1
2: B 2
库(plyr)
库(数据表)
dt试试这个:
> split(dt, dt[["p"]])
$A
p q
1: A 1
$B
p q
1: B 2
关于G.Grothendieck的回答,我很好奇split的表现如何:
dt <- data.table( p = rep( LETTERS[1:25], 1E6), q = 25*1E6, key = "p" )
system.time(
ll <- split(dt, dt[ ,p ] )
)
user system elapsed
5.237 1.340 6.563
system.time(
ll <- lapply( unique(dt[,p]), function(x) dt[x] )
)
user system elapsed
1.179 0.363 1.541
以下是一种更为面向数据的方法。表
方法:
setkey(dt, p)
dt[, list(list(dt[J(.BY[[1]])])), by = p]$V1
#[[1]]
# p q
#1: A 1
#
#[[2]]
# p q
#1: B 2
有更多的数据。表
样式替代上述样式,但这似乎是最快的-下面是与lappy
的比较:
dt <- data.table( p = rep( LETTERS[1:25], 1E6), q = 25*1E6, key = "p" )
microbenchmark(dt[, list(list(dt[J(.BY[[1]])])), by = p]$V1, lapply(unique(dt$p), function(x) dt[x]), times = 10)
#Unit: seconds
# expr min lq median uq max neval
#dt[, list(list(dt[J(.BY[[1]])])), by = p]$V1 1.111385 1.508594 1.717357 1.966694 2.108188 10
# lapply(unique(dt$p), function(x) dt[x]) 1.871054 1.934865 2.216192 2.282428 2.367505 10
dt哦,这很简单:-)我只是想知道性能,因为split没有使用数据表语法和功能。但你的回答实际上给了我正确方向的暗示。非常感谢!plyr是一个单独的包,用于轻松地在不同的数据结构之间进行转换。data.table作为高效/增强的data.frame实现。这是它的唯一目的。因此,没有内部有效的方法来做到这一点。您已经展示了(lappy)一个人可以做什么。为什么要拆分data.table?这违背了使用data.table的全部目的(通过避免拷贝来提高效率)。@Roland我完全同意。也许我的例子不够清楚。实际上,我想做的是对一系列数据执行操作。表子集了一些操作,这些操作最终构造了新的引用类
对象,我想将这些对象作为列表返回。+1用于使用。BY
,这是我还没有学会如何使用的.VAR
之一。我不喜欢语法,但这最能回答我的问题。我刚刚意识到dt[,list(list(…)),by=p]
不仅是我问题的最佳答案,也是最完美的答案。结果列V1
甚至可能包含任何类型的对象(原语、S3、S4、引用类对象等)。也就是说,我更讨厌语法:-)@Beasterfield你到底讨厌什么语法?你期望的是什么,或者为什么它没有达到你的期望呢?这并不是说它不像dlply
那么容易使用,而是在美学上我更喜欢dlply(dt,“id”,foo)
而不是dt[,list(list(foo(.SD))),by=id]$V1
。
dt <- data.table( p = rep( LETTERS[1:25], 1E6), q = 25*1E6, key = "p" )
microbenchmark(dt[, list(list(dt[J(.BY[[1]])])), by = p]$V1, lapply(unique(dt$p), function(x) dt[x]), times = 10)
#Unit: seconds
# expr min lq median uq max neval
#dt[, list(list(dt[J(.BY[[1]])])), by = p]$V1 1.111385 1.508594 1.717357 1.966694 2.108188 10
# lapply(unique(dt$p), function(x) dt[x]) 1.871054 1.934865 2.216192 2.282428 2.367505 10