在数据子集上应用函数的最有效方法(ddply的替代方法)

时间:2017-08-11 11:08:58

标签: r dataframe datatable dplyr plyr

我有相当多的数据集,其中随着时间报告不同对象的值。此外,价值本身每年可以多次测量。我只对一年内某个对象的取平均估值感兴趣。我的问题是,由于数据的大小,在所选子集上应用函数需要相当长的时间。有没有更有效的方法来做到这一点?我在某处读到使用data.table应该加快这个过程,但是我的玩具示例并非如此。

玩具示例(+基准测试):

library(data.table)
library(dplyr)

time_taken_df = c()
time_taken_dt = c()

test_data <- data.frame(id = round(runif(1000, 1,10), 0),
                        Value = round(runif(1000, 10, 50), 0),
                        Value_Year = round(runif(1000, 1999, 2010), 0))

for (i in 1:100){

  #Data Frame
  test_data <- as.data.frame(test_data)

  start_time_df <- Sys.time()

  test_data <- test_data %>%
    ddply(.(id, Value_Year), mutate, new_val = mean(Value))

  end_time_df <- Sys.time()

  #Data Table
  test_data <- as.data.table(test_data)

  start_time_dt <- Sys.time()

  test_data <- test_data %>%
    ddply(.(id, Value_Year), mutate, new_val = mean(Value))

  end_time_dt <- Sys.time()

  #Results
  time_taken_df[i] <- end_time_df - start_time_df
  time_taken_dt[i] <- end_time_dt - start_time_dt
}


mean(time_taken_df)
mean(time_taken_dt)

欢迎任何有关如何实现更快性能的建议!

注意:

  • 我将实际估值日期减少到估值年份,以提高示例的清晰度。

  • 所需的输出是 data.frame ,因为后来在分析中使用了其他特征。

1 个答案:

答案 0 :(得分:0)

正如 Imo user3293236 在评论中指出的那样,data.table显着提高了效果。使用:

setDT(test_data)[, myAvg := mean(Value), by=.(id, Value_Year)]

或仅仅test_data已经是data.table

data_table %>%
    [, myAvg := mean(Value), by=.(id, Value_Year)]

dplyrdata.table

之间的比较
mean(time_taken_df)
[1] 1.357766 

mean(time_taken_dt) 
[1] 0.003700418