J'ai les données suivantes:
data.frame(df, episode = letters[cumsum(c(1L, diff(df$week) > 1L))]) week episode 1 1 a 2 2 a 3 3 a 4 4 a 5 1 a 6 2 a 7 3 a 8 4 a 9 1 a 10 2 a 11 3 a 12 4 a
Je veux étiqueter chaque série consécutive de 1: 4 avec une lettre pour que le résultat soit le suivant:
week episode 1 1 a 2 2 a 3 3 a 4 4 a 5 1 b 6 2 b 7 3 b 8 4 b 9 1 c 10 2 c 11 3 c 12 4 c
3 Réponses :
Si c'est déjà dans une séquence, alors faites simplement le cumul du vecteur logique ( week == 1
)
df$episode <- letters[cumsum(df$week == 1)]
Ou en utilisant base R
(sans packages supplémentaires)
library(dplyr) df %>% mutate(episode = letters[cumsum(week == 1)]) # week episode #1 1 a #2 2 a #3 3 a #4 4 a #5 1 b #6 2 b #7 3 b #8 4 b #9 1 c #10 2 c #11 3 c #12 4 c
Merci qui fonctionne! Pour ma compréhension, comment le cumul du vecteur logique semaine == 1 donne-t-il ce résultat?
@fega df $ week == 1
renvoie un vecteur logique de TRUE / FALSE. un TRUE / FALSE est stocké sous la forme 1/0. Quand nous faisons cumsum
, cela ajoute 1 là où il y en a 1
Une autre possibilité de dplyr
pourrait être:
df$episode = letters[ceiling(seq_along(df$week)/4)]
Ou la même chose avec base R
:
df %>% mutate(episode = letters[ceiling(seq_along(week)/4)])
Or:
df$episode = letters[gl(length(df$week)/4, 4)]
Ou la même chose avec base R
:
df %>% mutate(episode = letters[gl(n()/4, 4)]) week episode 1 1 a 2 2 a 3 3 a 4 4 a 5 1 b 6 2 b 7 3 b 8 4 b 9 1 c 10 2 c 11 3 c 12 4 c
Vous pouvez utiliser rowid
du package data.table
library(data.table) setDT(df) df[, episode := letters[rowid(week)]] # week episode # 1: 1 a # 2: 2 a # 3: 3 a # 4: 4 a # 5: 1 b # 6: 2 b # 7: 3 b # 8: 4 b # 9: 1 c # 10: 2 c # 11: 3 c # 12: 4 c
C'est une manière astucieuse