创建一个函数,将间隔分解为每天explode
一行的数据框。用于应用于生成数据帧列表的每个间隔,每个间隔一个。接下来将列表中的数据框合并为一个大数据框,每天一行。最后汇总成每一年/月的一行:Map
explode
rbind
by.date
by.date
library(zoo) # as.yearmon
explode <- function(start, end, amount) {
dates <- seq(start, end, "day")
data.frame(dates, yearmon = as.yearmon(dates), amount = amount / length(dates))
}
by.date <- do.call("rbind", Map(explode, df$start, df$end, df$amount))
aggregate(amount ~ yearmon, by.date, sum)
使用问题中的数据(假设 2010 年的发生应该是 2013 年),我们得到:
yearmon amount
1 Jan 2013 100.00000
2 Feb 2013 94.91525
3 Mar 2013 105.08475
4 Apr 2013 100.00000
5 May 2013 100.00000
更新:如果内存有问题,请explode
改用它。它首先在内部聚合,explode
因此它的输出更小。我们还删除了该dates
列,DF
因为它仅用于调试:
explode <- function(start, end, amount) {
dates <- seq(start, end, "day")
DF <- data.frame(yearmon = as.yearmon(dates), amount = amount / length(dates))
aggregate(amount ~ yearmon, DF, sum)
}
更新2:这是另一个尝试。它使用rowsum
专门用于汇总总和的。在我的测试中,这个在帖子中的数据上运行速度快了 10 倍。
explode2 <- function(start, end, amount) {
dates <- seq(start, end, "day")
n <- length(dates)
rowsum(rep(amount, n) / n, format(dates, "%Y-%m"))
}
by.date <- do.call("rbind", Map(explode2, df$start, df$end, df$amount))
rowsum(by.date, rownames(by.date))