我試圖根據ID計數連續的幾天無效(consecDaysInactive
)。在R中創建一個計數器變量,並按條件重置
我已經創建了一個指示變量inactive
,在ID爲非活動狀態的日期爲1,在活動狀態時爲0。我也有一個id變量和一個日期變量。我的分析數據集將包含數十萬行,因此效率將非常重要。
我試圖創建的邏輯如下:
- 每個ID,如果用戶是活動的,
consecDaysInactive
= 0 - 每個ID,如果用戶是不活動的,並且是在先前的天活性,
consecDaysInactive
= 1 - 每個ID,如果用戶是在前一天無活性的,
consecDaysInactive
= 1 +#先前不活動的連續天 consecDaysInactive
應該重置爲0的id新值。
我已經能夠創建一個累計總和,但無法得到它重置在0後非活動== 0行。
我已經在下面說明了我想要的結果(consecDaysInactive
)以及我能夠以編程方式實現的結果(bad_consecDaysInactive
)。
library(dplyr)
d <- data.frame(id = c(1,1,1,1,1,1,1,1,2,2,2,2,2,2,2,2), date=as.Date(c('2017-01-01','2017-01-02','2017-01-03','2017-01-04','2017-01-05','2017-01-06','2017-01-07','2017-01-08','2017-01-01','2017-01-02','2017-01-03','2017-01-04','2017-01-05','2017-01-06','2017-01-07','2017-01-08')), inactive=c(0,0,0,1,1,1,0,1,0,1,1,1,1,0,0,1), consecDaysInactive=c(0,0,0,1,2,3,0,1,0,1,2,3,4,0,0,1))
d <- d %>%
group_by(id) %>%
arrange(id, date) %>%
do(data.frame(., bad_consecDaysInactive = cumsum(ifelse(.$inactive==1, 1,0))
)
)
d
其中consecDaysInactive
迭代由1對每個連續的天無活性的,但重置爲0的每個日期用戶是活動的,並且復位爲0的id新值。由於輸出如下所示,我無法獲得bad_consecDaysInactive
重置爲0 - 例如排
id date inactive consecDaysInactive bad_consecDaysInactive
<dbl> <date> <dbl> <dbl> <dbl>
1 1 2017-01-01 0 0 0
2 1 2017-01-02 0 0 0
3 1 2017-01-03 0 0 0
4 1 2017-01-04 1 1 1
5 1 2017-01-05 1 2 2
6 1 2017-01-06 1 3 3
7 1 2017-01-07 0 0 3
8 1 2017-01-08 1 1 4
9 2 2017-01-01 0 0 0
10 2 2017-01-02 1 1 1
11 2 2017-01-03 1 2 2
12 2 2017-01-04 1 3 3
13 2 2017-01-05 1 4 4
14 2 2017-01-06 0 0 4
15 2 2017-01-07 0 0 4
16 2 2017-01-08 1 1 5
我也算(而且試過)內group_by()
& do()
遞增的變量,但由於do()
是不重複的,我不能讓我的櫃檯,讓過去2:
d2 <- d %>%
group_by(id) %>%
do(data.frame(., bad_consecDaysInactive2 = ifelse(.$inactive == 0, 0, ifelse(.$inactive==1,.$inactive+lag(.$inactive), .$inactive))))
d2
其產生,如上文所述:
id date inactive consecDaysInactive bad_consecDaysInactive bad_consecDaysInactive2
<dbl> <date> <dbl> <dbl> <dbl> <dbl>
1 1 2017-01-01 0 0 0 0
2 1 2017-01-02 0 0 0 0
3 1 2017-01-03 0 0 0 0
4 1 2017-01-04 1 1 1 1
5 1 2017-01-05 1 2 2 2
6 1 2017-01-06 1 3 3 2
7 1 2017-01-07 0 0 3 0
8 1 2017-01-08 1 1 4 1
9 2 2017-01-01 0 0 0 0
10 2 2017-01-02 1 1 1 1
11 2 2017-01-03 1 2 2 2
12 2 2017-01-04 1 3 3 2
13 2 2017-01-05 1 4 4 2
14 2 2017-01-06 0 0 4 0
15 2 2017-01-07 0 0 4 0
16 2 2017-01-08 1 1 5 1
正如你看到的,我的迭代器bad_consecDaysInactive2
復位在0,但不會增加過去2!如果有data.table解決方案,我也很樂意聽到它。
像這個時間差? '庫(data.table); setDT(d)[,consecDaysInactive2:= cumsum(inactive),by =。(id,cumsum(!inactive))]' – chinsoon12
'library(data.table); setDT(d)[,v:= if(inactive [1])seq.int(.N)else 0L,by = rleid(inactive)]' – Frank
感謝chinsoon12和Frank - 這兩個都很好。我將以此爲契機探索data.table庫。 @Frank,關於你將這篇文章標記爲重複,我認爲這與你標記的文章不同,OP要求在dplyr中使用data.table函數,目標是使一個常量增加不同的ID值。我嘗試的操作是不同的,我沒有要求在dplyr中使用data.table方法; dplyr是我嘗試過的方法,但無法實現我的目標,因此是個問題。再次感謝您的幫助。 – rsty