更快的方法来创建通过id聚合列的变量

ilp*_*ipe 6 performance aggregate r plyr

有更快的方法吗?我想这是不必要的慢,并且这样的任务可以通过基本功能完成.

df <- ddply(df, "id", function(x) cbind(x, perc.total = sum(x$cand.perc)))
Run Code Online (Sandbox Code Playgroud)

我是很新的R.我已经看过了by(),aggregate()tapply(),但并没有让他们在所有或我想要的方式工作.我希望将总和附加到原始数据帧,而不是返回较短的向量.做这个的最好方式是什么?

编辑:这是应用于我的数据的答案的速度比较.

> # My original solution
> system.time( ddply(df, "id", function(x) cbind(x, perc.total = sum(x$cand.perc))) )
   user  system elapsed 
 14.405   0.000  14.479 

> # Paul Hiemstra
> system.time( ddply(df, "id", transform, perc.total = sum(cand.perc)) )
   user  system elapsed 
 15.973   0.000  15.992 

> # Richie Cotton
> system.time( with(df, tapply(df$cand.perc, df$id, sum))[df$id] )
   user  system elapsed 
  0.048   0.000   0.048 

> # John
> system.time( with(df, ave(cand.perc, id, FUN = sum)) )
       user  system elapsed 
      0.032   0.000   0.030 

> # Christoph_J
> system.time( df[ , list(perc.total = sum(cand.perc)), by="id"][df])
   user  system elapsed 
  0.028   0.000   0.028 
Run Code Online (Sandbox Code Playgroud)

Chr*_*h_J 12

由于你是R的新手,速度显然是一个问题,我推荐这个data.table包,这真的很快.在一行中解决问题的一种方法如下:

library(data.table)
DT <- data.table(ID = rep(c(1:3), each=3),
                 cand.perc = 1:9,
                 key="ID")
DT <- DT[ , perc.total := sum(cand.perc), by = ID]
DT
      ID Perc.total cand.perc
 [1,]  1          6         1
 [2,]  1          6         2
 [3,]  1          6         3
 [4,]  2         15         4
 [5,]  2         15         5
 [6,]  2         15         6
 [7,]  3         24         7
 [8,]  3         24         8
 [9,]  3         24         9
Run Code Online (Sandbox Code Playgroud)

免责声明:我不是一个data.table专家(还有;-),所以可能有更快的方法来做到这一点.如果您有兴趣使用该软件包,请查看软件包网站以开始使用:http://datatable.r-forge.r-project.org/


Joh*_*ohn 6

对于任何类型的聚合,您希望结果向量的长度与输入向量的长度相同,并且在分组向量ave中分组的副本是您想要的.

df$perc.total <- ave(df$cand.perc, df$id, FUN = sum)
Run Code Online (Sandbox Code Playgroud)