我想在下面的数据框中添加一个新列,以计算每个月的最大干法术长度。 这是我的数据框的样子:
day month year rr spell spell1
1 1 1981 0 dry 1
2 1 1981 0 dry 1
3 1 1981 0 dry 1
4 1 1981 1.1 dry 0
5 1 1981 0 dry 1
6 1 1981 0 dry 1
7 1 1981 0 dry 1
8 1 1981 0 dry 1
9 1 1981 2.7 dry 0
10 1 1981 0 dry 1
这是我需要的输出:
month year spell_length
1 1981 3
1 1981 4
1 1981 1
这是我到目前为止所做的:
group_by(df, year, month, spell1) %>%
summarise(spell2 = sum(spell1, na.rm = TRUE))
这是结果:
year month spell1 spell_length
<int> <int> <dbl> <dbl>
1 1981 1 1 31
2 1981 2 0 0
3 1981 2 1 27
4 1981 3 0 0
5 1981 3 1 25
6 1981 4 0 0
数据
df <- read.table(h= T, text="day month year rr spell spell1
1 1 1981 0 dry 1
2 1 1981 0 dry 1
3 1 1981 0 dry 1
4 1 1981 1.1 dry 0
5 1 1981 0 dry 1
6 1 1981 0 dry 1
7 1 1981 0 dry 1
8 1 1981 0 dry 1
9 1 1981 2.7 dry 0
10 1 1981 0 dry 1")
答案 0 :(得分:7)
一种选择是按“ spell”的“ run-length-id”分组({{1}中的rleid
-当该列中的值更改时创建新的分组ID),{{ 1}}的'spell1'为0的行中,得到data.table
filter
或使用n()
中的library(dplyr)
library(data.table)
df1 %>%
group_by(year, month, grp = rleid(spell1)) %>%
filter(spell1 ==1) %>%
summarise(spell_length = n()) %>%
ungroup %>%
select(-grp)
# A tibble: 3 x 3
# year month spell_length
# <int> <int> <int>
#1 1981 1 3
#2 1981 1 4
#3 1981 1 1
rle
注意:当'spell1'值不同时,此解决方案也适用
答案 1 :(得分:7)
使用dplyr
,我们可以使用cumsum
在每次出现0时创建组,并将每个组中spells
的数量相加。
library(dplyr)
df %>%
group_by(month, year, group = cumsum(spell1 == 0)) %>%
summarise(spell_length = sum(spell1)) %>%
ungroup() %>%
select(-group)
# month year spell_length
# <int> <int> <int>
#1 1 1981 3
#2 1 1981 4
#3 1 1981 1
答案 2 :(得分:4)
使用@akrun的基本思想,但不使用data.table::rleid()
:
df %>%
group_by(year, month, rleid = with(rle(spell1), rep(seq_along(lengths), lengths))) %>%
filter(spell1 > 0) %>%
ungroup() %>%
count(month, year, rleid, name = "spell_length") %>%
select(-rleid)
month year spell_length
<int> <int> <int>
1 1 1981 3
2 1 1981 4
3 1 1981 1
或者:
df %>%
group_by(year, month, rleid = with(rle(spell1), rep(seq_along(lengths), lengths))) %>%
filter(spell1 > 0) %>%
summarise(spell_length = length(rleid)) %>%
ungroup() %>%
select(-rleid)
答案 3 :(得分:4)
以下是使用dplyr::count
的选项:
library(dplyr)
count(df, month, year, grp = cumsum(spell1 == 0), zero = spell1==0) %>%
filter(!zero) %>%
select(-zero, - grp)
# # A tibble: 3 x 3
# month year n
# <int> <int> <int>
# 1 1 1981 3
# 2 1 1981 4
# 3 1 1981 1
或者在基数R中:
res <- aggregate(day ~ month + year + cumsum(spell1 == 0) + (spell1==0), df, length)
res[!res[[4]],-(3:4)]
# month year day
# 1 1 1981 3
# 2 1 1981 4
# 3 1 1981 1