我有一些这样的数据:
data <- tibble(a = 1:100)
a
--
1
2
3
4
5
6
7
...
等...
有没有优雅的方法来创建一个n个前导值之和的变量?我的意思是这样的:
data %>% mutate(b = lead(a,1) + lead(a,2) + lead(a,3) + ... + lead(a,n))
例如,在n = 2的情况下,我会得到:
a b
--------------
1 2+3 = 5
2 3+4 = 7
3 4+5 = 9
4 5+6 = 11
5 6+7 = 13
6 7+8 = 15
7 8+9 = 17
...
提前致谢!
答案 0 :(得分:3)
我们正在危险地接近重新创建stats::filter
dplyr
掩盖的功能:
stats::filter(1:10, c(rep(1,2),0), sides=1)
#Time Series:
#Start = 1
#End = 10
#Frequency = 1
# [1] NA NA 5 7 9 11 13 15 17 19
这是一个与输出完全匹配的小功能:
sumnahead <- function(x,n) {
rev(stats::filter(rev(x), c(0,rep(1,n)), sides=1))
}
sumnahead(1:10,2)
#[1] 5 7 9 11 13 15 17 19 NA NA
它也很快,因为它可以用于编译代码:
system.time(sumnahead(1:1e7,50))
# user system elapsed
# 2.28 0.22 2.53
system.time(lead_n(1:1e7,50))
# user system elapsed
# 6.02 4.07 10.13
答案 1 :(得分:1)
使用快速功能生成所有前导向量并将它们添加到一起:
lead_n = function(x, n = 1) {
leads = lapply(1:n, function(i) lead(x, i))
Reduce(`+`, leads)
}
data %>%
mutate(b = lead_n(a, 2))
输出:
a b
<int> <int>
1 1 5
2 2 7
3 3 9
4 4 11
5 5 13
6 6 15
7 7 17
8 8 19
9 9 21
10 10 23
答案 2 :(得分:1)
这是左对齐的滚动总和偏移一。 lead
一个用来排除当前值。
library(dplyr)
data <- tibble(a = 1:100)
data %>% mutate(b = lead(zoo::rollsum(a, 2, fill = NA, align = 'left')))
#> # A tibble: 100 x 2
#> a b
#> <int> <int>
#> 1 1 5
#> 2 2 7
#> 3 3 9
#> 4 4 11
#> 5 5 13
#> 6 6 15
#> 7 7 17
#> 8 8 19
#> 9 9 21
#> 10 10 23
#> # ... with 90 more rows