结果馈送滚动窗口或带有累加的滚动应用

问题描述 投票:1回答:2

假设我有以下动物园对象:

x.orig <- read.zoo(data.frame(date=seq(as.Date('2020-01-01'), as.Date('2020-01-10'), 1), v=c(1,2,3,100,4,5,1000,8,8,10)))
2020-01-01 2020-01-02 2020-01-03 2020-01-04 2020-01-05 2020-01-06 2020-01-07 2020-01-08 2020-01-09 2020-01-10 
         1          2          3        100          4          5       1000          8          8         10 

我想如下计算width=seq_along(x.orig)的滚动总和:

2020-01-01 1
2020-01-02 1 + 2                                   #2020-01-01 + 2020-01-02
2020-01-03 1 + (1 + 2) + 3                         #2020-01-01 + 2020-01-02 + 2020-01-03
2010-01-04 1 + (1 + 2) + (1 + (1 + 2) + 3) + 100   #2020-01-01 + 2020-01-02 + 2020-01-03 + 2020-01-04
...

我想这样做的方法是以某种方式对x进行结果馈送,以便在每个rollapply循环后更新x,以便下一个rollapply迭代在其窗口中拾取修改后的值,但不确定如何写...

r dataframe zoo
2个回答
1
投票

我不认为这很常见,因此可能不会有此功能,但是您可以使用Rcpp修改自己的快速功能,这是一个示例:

library(data.table)
library(Rcpp)

DT <- data.table(date=seq(as.Date('2020-01-01'), as.Date('2020-01-10'), 1),
                 v=c(1,2,3,100,4,5,1000,8,8,10))
DT[, week := 1:.N %/% 7] # create a week column (you can adapt this to your needs)

# Add your logic to a cpp function
cppFunction("
    IntegerVector roll_cumsum(IntegerVector x) {
        int n = x.size();
        int cumsum = x[0];
        IntegerVector y = clone(x);
        for (int i = 1; i < n; ++i) {
            y[i] = x[i] + cumsum;
            cumsum += y[i];
        }
        return y;
    }
")

DT[, result := roll_cumsum(v), by = week][]

0
投票

这是我的尝试。理想情况下,我想在每次迭代后都修改x.orig,但无法正常工作,因此又创建了一个名为latest的变量。我怀疑这是最好的方法:

library(zoo)

latest <- x.orig
rollapplyr(x.orig, width = seq_along(x.orig), function(x) {
   #browser()
   x <- latest[index(x)]
   v <- sum(x)
   if (!is.na(v))
     latest[last(index(x))] <<- v
   latest[last(index(x))]
})

2020-01-01 2020-01-02 2020-01-03 2020-01-04 2020-01-05 2020-01-06 2020-01-07 2020-01-08 2020-01-09 2020-01-10 
         1          3          7        111        126        253       1501       2010       4020       8042
© www.soinside.com 2019 - 2024. All rights reserved.