计数值出现在组中最后 x 行的次数
Count number of times value has appeared in last x rows in group
我有一个像下面这样的数据框
dataDF <- data.frame(
group = c(rep('a', 10), rep('b', 10)),
value = c(4, 4, 4, 3, 4, 3, 4, 3, 3, 3,
3, 1, 1, 1, 3, 1, 3, 2, 3, 1)
)
我想找出每个值在过去 5 个条目中出现在组中的次数(或者,如果它还没有 5 行,那么到目前为止的总计数)。
所以我最终会得到:
group value number_l5
1 a 4 1
2 a 4 2
3 a 4 3
4 a 3 1
5 a 4 4
6 a 3 2
7 a 4 3
8 a 3 3
9 a 3 3
10 a 3 4
11 b 3 1
12 b 1 1
13 b 1 2
14 b 1 3
15 b 3 2
16 b 1 4
17 b 3 2
18 b 2 1
19 b 3 3
20 b 1 2
因此前三行,每行的值为 4,因此累积计数为 1、2、3。第 4 行是我们第一次看到 3,所以计数为 1。当你经过第 5 行时,我们只查看过去的 5 行,所以在第 7 行中,我们计算从第 3 行到第 4 行的 4 的数量7,得到 3。一旦你到达第 11 行,一个新组 'b' 开始,我们重新开始。
如果可能,想与 dplyr
和 group_by
合作
提前致谢
编辑:最初要求比例,为了更简单,希望更清楚,已更改为要求数量。对任何混淆表示歉意!
您可以为此使用 zoo::rollapply
;这里设置 window 大小为 5
和 partial=T
以包括前几个元素; sum(v == tail(v, 1))
是计算每个window中最后一个元素出现的次数:
library(dplyr)
library(zoo)
dataDF %>%
group_by(group) %>%
mutate(proportion = rollapply(value, 5, function(v) sum(v == tail(v, 1)), partial=T, align='right'))
# A tibble: 20 x 3
# Groups: group [2]
# group value proportion
# <fct> <dbl> <int>
# 1 a 4 1
# 2 a 4 2
# 3 a 4 3
# 4 a 3 1
# 5 a 4 4
# 6 a 3 2
# 7 a 4 3
# 8 a 3 3
# 9 a 3 3
#10 a 3 4
#11 b 3 1
#12 b 1 1
#13 b 1 2
#14 b 1 3
#15 b 3 2
#16 b 1 4
#17 b 3 2
#18 b 2 1
#19 b 3 3
#20 b 1 2
dataDF%>%
group_by(group)%>%
mutate(i=1:n(),value1=list(value))%>%
group_by(group,i)%>%
mutate(proportion=mean(value==unlist(value1)[if(i<5)1:i else i:(i-4)]))%>%
ungroup()%>%
select(-i,-value1)
# A tibble: 20 x 3
group value proportion
<fct> <dbl> <dbl>
1 a 4. 1.00
2 a 4. 1.00
3 a 4. 1.00
4 a 3. 0.250
5 a 4. 0.800
6 a 3. 0.400
7 a 4. 0.600
8 a 3. 0.600
9 a 3. 0.600
10 a 3. 0.800
11 b 3. 1.00
12 b 1. 0.500
13 b 1. 0.667
14 b 1. 0.750
15 b 3. 0.400
16 b 1. 0.800
17 b 3. 0.400
18 b 2. 0.200
19 b 3. 0.600
20 b 1. 0.400
>
我有一个像下面这样的数据框
dataDF <- data.frame(
group = c(rep('a', 10), rep('b', 10)),
value = c(4, 4, 4, 3, 4, 3, 4, 3, 3, 3,
3, 1, 1, 1, 3, 1, 3, 2, 3, 1)
)
我想找出每个值在过去 5 个条目中出现在组中的次数(或者,如果它还没有 5 行,那么到目前为止的总计数)。
所以我最终会得到:
group value number_l5
1 a 4 1
2 a 4 2
3 a 4 3
4 a 3 1
5 a 4 4
6 a 3 2
7 a 4 3
8 a 3 3
9 a 3 3
10 a 3 4
11 b 3 1
12 b 1 1
13 b 1 2
14 b 1 3
15 b 3 2
16 b 1 4
17 b 3 2
18 b 2 1
19 b 3 3
20 b 1 2
因此前三行,每行的值为 4,因此累积计数为 1、2、3。第 4 行是我们第一次看到 3,所以计数为 1。当你经过第 5 行时,我们只查看过去的 5 行,所以在第 7 行中,我们计算从第 3 行到第 4 行的 4 的数量7,得到 3。一旦你到达第 11 行,一个新组 'b' 开始,我们重新开始。
如果可能,想与 dplyr
和 group_by
合作
提前致谢
编辑:最初要求比例,为了更简单,希望更清楚,已更改为要求数量。对任何混淆表示歉意!
您可以为此使用 zoo::rollapply
;这里设置 window 大小为 5
和 partial=T
以包括前几个元素; sum(v == tail(v, 1))
是计算每个window中最后一个元素出现的次数:
library(dplyr)
library(zoo)
dataDF %>%
group_by(group) %>%
mutate(proportion = rollapply(value, 5, function(v) sum(v == tail(v, 1)), partial=T, align='right'))
# A tibble: 20 x 3
# Groups: group [2]
# group value proportion
# <fct> <dbl> <int>
# 1 a 4 1
# 2 a 4 2
# 3 a 4 3
# 4 a 3 1
# 5 a 4 4
# 6 a 3 2
# 7 a 4 3
# 8 a 3 3
# 9 a 3 3
#10 a 3 4
#11 b 3 1
#12 b 1 1
#13 b 1 2
#14 b 1 3
#15 b 3 2
#16 b 1 4
#17 b 3 2
#18 b 2 1
#19 b 3 3
#20 b 1 2
dataDF%>%
group_by(group)%>%
mutate(i=1:n(),value1=list(value))%>%
group_by(group,i)%>%
mutate(proportion=mean(value==unlist(value1)[if(i<5)1:i else i:(i-4)]))%>%
ungroup()%>%
select(-i,-value1)
# A tibble: 20 x 3
group value proportion
<fct> <dbl> <dbl>
1 a 4. 1.00
2 a 4. 1.00
3 a 4. 1.00
4 a 3. 0.250
5 a 4. 0.800
6 a 3. 0.400
7 a 4. 0.600
8 a 3. 0.600
9 a 3. 0.600
10 a 3. 0.800
11 b 3. 1.00
12 b 1. 0.500
13 b 1. 0.667
14 b 1. 0.750
15 b 3. 0.400
16 b 1. 0.800
17 b 3. 0.400
18 b 2. 0.200
19 b 3. 0.600
20 b 1. 0.400
>