修改数据:
structure(list(hour = c(0L, 1L, 1L, 1L, 0L, 1L, 1L, 1L, 0L, 0L,
1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 1L, 1L, 1L, 0L, 1L, 1L, 0L, 0L), cs = c(0L, 0L, 0L, 0L,
0L, 1L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L,
1L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 0L, 0L
), cs_acum = c(0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
0L, 0L, 0L, 0L, 1L, 2L, 0L, 0L), cs_wanted = c(0L, 0L, 0L, 0L,
0L, 1L, 2L, 3L, 0L, 0L, 4L, 5L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L,
3L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 0L, 0L
), cs_acum2 = c(0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 4L, 5L,
0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 0L, 0L, 0L, 0L, 0L,
1L, 2L, 3L, 0L, 4L, 5L, 0L, 0L)), .Names = c("hour", "cs", "cs_acum",
"cs_wanted", "cs_acum2"), class = c("data.table", "data.frame"
), row.names = c(NA, -36L), .internal.selfref = <pointer: 0x00000000001f0788>)
Run Code Online (Sandbox Code Playgroud)
cs_acum是cs重新启动时的累计和为0.
df1$cs_acum <- with(df1, ave(df1$cs, cumsum(df1$cs == 0), FUN = cumsum))
Run Code Online (Sandbox Code Playgroud)
如果在1 hour 的累积之后有cs 5行中的1的值已经停止,我需要这个累积继续.
期望的输出是col cs_wanted.
进一步说明:çs_acum是cs符合某些标准的小时(行f )的累积.在此之后,它与之无关cs,它与col:相关hour.如果在停止后5小时窗口中的值为1,则应继续累积.
可能是一个新的功能,hour从位置cs_acum轮流到0 检查五条线,将按顺序继续从它停止的位置累积cs_acum.
可能的步骤:
如果值为1,则
找到累积停止的位置,
以小时为单位查看下五行
,继续累计该行,
在接下来的五个小时再查看,
如果没有值1,则不执行任何操作.
新数据:
df3 <- structure(list(hour = c(1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1),
cs = c(0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1),
cs_acum = c(0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13),
cs_acum2 = c(0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 0, 0, 0, 8, 9, 10, 11, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28)),
.Names = c("hour", "cs", "cs_acum", "cs_acum2"), class = "data.frame", row.names = c(NA, -68L))
Run Code Online (Sandbox Code Playgroud)
使用:
library(data.table)
rl <- rle(df1$hour)
setDT(df1)[, grp := rleid(rep(rl$lengths >5 & rl$values == 0, rl$lengths))
][hour == 1, cs_acum2 := cumsum(hour), grp
][is.na(cs_acum2), cs_acum2 := 0][]
Run Code Online (Sandbox Code Playgroud)
得到:
hour cs cs_acum cs_wanted grp cs_acum2
1: 1 1 1 1 1 1
2: 1 1 2 2 1 2
3: 1 1 3 3 1 3
4: 0 0 0 0 1 0
5: 0 0 0 0 1 0
6: 1 0 0 4 1 4
7: 1 0 0 5 1 5
8: 0 0 0 0 2 0
9: 0 0 0 0 2 0
10: 0 0 0 0 2 0
11: 0 0 0 0 2 0
12: 0 0 0 0 2 0
13: 0 0 0 0 2 0
14: 1 1 1 1 3 1
15: 1 1 2 2 3 2
16: 1 1 3 3 3 3
17: 0 0 0 0 3 0
Run Code Online (Sandbox Code Playgroud)
说明:
setDT(df1).rl <- rle(d1$hour)和grp := rleid(rep(rl$lengths >5 & rl$values == 0, rl$lengths))创建一个分组变量,仅当有超过5个零时才会更改.hour == 1并创建一个获取累积总和cumsum(hour).如果您的值hour只是1's和0's',那么您也可以使用seq_along或创建一个具有1:.N相同结果的计数器.is.na(cs_acum2), cs_acum2 := 0将NA更改为零.更新1:对于新示例数据(df2):
rl2 <- rle(df2$hour)
setDT(df2)[, `:=` (rn = .I, grp = rleid(rep(rl2$lengths >5 & rl2$values == 0, rl2$lengths)))
][hour == 1 & rn >= df2[, .I[cs == 1]][1], cs_acum2 := cumsum(hour), grp
][is.na(cs_acum2), cs_acum2 := 0][, c('rn','grp') := NULL][]
Run Code Online (Sandbox Code Playgroud)
这使:
hour cs cs_acum cs_wanted cs_acum2
1: 0 0 0 0 0
2: 1 0 0 0 0
3: 1 0 0 0 0
4: 1 0 0 0 0
5: 0 0 0 0 0
6: 1 1 1 1 1
7: 1 1 2 2 2
8: 1 1 3 3 3
9: 0 0 0 0 0
10: 0 0 0 0 0
11: 1 0 0 4 4
12: 1 0 0 5 5
13: 0 0 0 0 0
14: 0 0 0 0 0
15: 0 0 0 0 0
16: 0 0 0 0 0
17: 0 0 0 0 0
18: 0 0 0 0 0
19: 1 1 1 1 1
20: 1 1 2 2 2
21: 1 1 3 3 3
22: 0 0 0 0 0
Run Code Online (Sandbox Code Playgroud)
就我的理解是是,cumsum中hour只允许第一次出现后启动cs == 1.
补充说明:
rn = .I你创建一个rowindexnumber.df2[, .I[cs == 1]][1]cs == 1第一次给你rownumber .rn >= df2[, .I[cs == 1]][1]您只选择该点以后的行.更新2:关于最新(第四)数据集,您可以:
rl4 <- rle(df4$hour)
setDT(df4)[, grp := rleid(rep(rl4$lengths >5 & rl4$values == 0, rl4$lengths))]
i1 <- df4[, .I[cs == 1][1], grp][!is.na(V1)]$V1
i2 <- df4[, .I[1:.N==5], rleid(cs)]$V1[-1] + 1
df4[i1, cs.inc := 1
][i2, cs.inc := -1
][is.na(cs.inc), cs.inc := 0
][, cs.inc := cumsum(cs.inc)
][hour == 1 & cs.inc == 1, cs_acum3 := cumsum(hour), grp
][is.na(cs_acum3), cs_acum3 := 0][, c('grp','cs.inc') := NULL][]
Run Code Online (Sandbox Code Playgroud)
这使:
hour cs cs_acum cs_wanted cs_acum2 cs_acum3
1: 0 0 0 0 0 0
2: 1 0 0 0 0 0
3: 1 0 0 0 0 0
4: 1 0 0 0 0 0
5: 0 0 0 0 0 0
6: 1 1 1 1 1 1
7: 1 1 2 2 2 2
8: 1 1 3 3 3 3
9: 0 0 0 0 0 0
10: 0 0 0 0 0 0
11: 1 0 0 4 4 4
12: 1 0 0 5 5 5
13: 0 0 0 0 0 0
14: 0 0 0 0 0 0
15: 0 0 0 0 0 0
16: 0 0 0 0 0 0
17: 0 0 0 0 0 0
18: 0 0 0 0 0 0
19: 1 1 1 1 1 1
20: 1 1 2 2 2 2
21: 1 1 3 3 3 3
22: 0 0 0 0 0 0
23: 0 0 0 0 0 0
24: 0 0 0 0 0 0
25: 0 0 0 0 0 0
26: 0 0 0 0 0 0
27: 0 0 0 0 0 0
28: 0 0 0 0 0 0
29: 1 0 0 0 1 0
30: 1 0 0 0 2 0
31: 1 0 0 0 3 0
32: 0 0 0 0 0 0
33: 1 1 1 1 4 1
34: 1 1 2 2 5 2
35: 0 0 0 0 0 0
36: 0 0 0 0 0 0
Run Code Online (Sandbox Code Playgroud)
使用过的数据
第一个示例数据集:
df1 <- structure(list(hour = c(1L, 1L, 1L, 0L, 0L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L),
cs = c(1L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L),
cs_acum = c(1L, 2L, 3L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L),
cs_wanted = c(1L, 2L, 3L, 0L, 0L, 4L, 5L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L)),
.Names = c("hour", "cs", "cs_acum", "cs_wanted"), class = "data.frame", row.names = c(NA, -17L))
Run Code Online (Sandbox Code Playgroud)
第二个数据集:
df2 <- structure(list(hour = c(0L, 1L, 1L, 1L, 0L, 1L, 1L, 1L, 0L, 0L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L),
cs = c(0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L),
cs_acum = c(0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L),
cs_wanted = c(0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 4L, 5L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L)),
.Names = c("hour", "cs", "cs_acum", "cs_wanted"), class = "data.frame", row.names = c(NA, -22L))
Run Code Online (Sandbox Code Playgroud)
第四个数据集:
df4 <- structure(list(hour = c(0L, 1L, 1L, 1L, 0L, 1L, 1L, 1L, 0L, 0L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L, 1L, 1L, 0L, 0L),
cs = c(0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 0L, 0L),
cs_acum = c(0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 0L, 0L),
cs_wanted = c(0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 4L, 5L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 0L, 0L),
cs_acum2 = c(0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 4L, 5L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L, 2L, 3L, 0L, 4L, 5L, 0L, 0L)),
.Names = c("hour", "cs", "cs_acum", "cs_wanted", "cs_acum2"), class = "data.frame", row.names = c(NA, -36L))
Run Code Online (Sandbox Code Playgroud)