2017-01-24 2 views
1

J'ai des données qui incluent des dates (jj/mm/aaaa) et je souhaite résumer les données par année. Je suis sûr qu'il y a un moyen plus simple de le faire mais la route que j'ai prise est d'essayer de créer une nouvelle variable catégorielle en utilisant la fonction "couper".Créer une variable catégorielle à partir des données de date dans R

Par exemple:

# create sample dataframe 
dates<-c("01/01/2013", "01/02/2013", "01/01/2014", "01/02/2014", "01/01/2015", "01/02/2015") 
cases<-c(3,5,2,6,8,4) 
df<-as.data.frame(cbind(dates, cases)) 
df$dates <- as.Date(df$dates,"%d/%m/%Y") 

# categorise by year 
df$year <- cut(df$dates, c(2013-01-01, 2013-12-31, 2014-12-31, 2015-12-31)) 

Cela donne une erreur:

invalid specification of 'breaks' 

Comment puis-je dire R couper à différents intervalles "date"? Est-ce que mon approche de tout cela est fausse? Encore nouveau à R (désolé de la question de base).

Greg

+0

Votre argument 'breaks' est faux. L'entrée doit être soit des chaînes (qui pourraient fonctionner), soit des objets de date qui peuvent être facilement construits en utilisant des chaînes (voir la réponse de Leo P.). –

+0

Notez que le cbind s'assure que 'cases' devient un caractère et non un numérique. –

Répondre

0

À quoi devrait ressembler votre sortie?

Votre code fonctionne lorsque vous définissez vos pauses avec as.Date:

breaks <- as.Date(c("2013-01-01", "2013-12-31", "2014-12-31", "2015-12-31")) 

# categorise by year 
df$year <- cut(df$dates, breaks) 

     dates cases  year 
1 2013-01-01  3 2013-01-01 
2 2013-02-01  5 2013-01-01 
3 2014-01-01  2 2013-12-31 
4 2014-02-01  6 2013-12-31 
5 2015-01-01  8 2014-12-31 
6 2015-02-01  4 2014-12-31 

Je devine que vous voulez votre variable year à un aspect différent, si? Vous pouvez définir labels lors de l'utilisation cut:

# categorise by year 
df$year <- cut(df$dates, breaks, labels = c(2013, 2014, 2015)) 

     dates cases year 
1 2013-01-01  3 2013 
2 2013-02-01  5 2013 
3 2014-01-01  2 2014 
4 2014-02-01  6 2014 
5 2015-01-01  8 2015 
6 2015-02-01  4 2015 
1

si vous êtes à la recherche de l'année, peut-être cela aide:

df$year <- format(df$dates, format="%Y")

 dates cases year 
1 2013-01-01  3 2013 
2 2013-02-01  5 2013 
3 2014-01-01  2 2014 
4 2014-02-01  6 2014 
5 2015-01-01  8 2015 
6 2015-02-01  4 2015 
1

Une solution simple serait en utilisant le paquet dplyr. Voici un exemple simple:

library(dplyr) 

df_grouped <- df %>% 
    mutate(
    dates = as_date(dates), 
    cases = as.numeric(cases)) %>% 
    group_by(year = year(dates)) %>% 
    summarise(tot_cases = sum(cases)) 

Dans la déclaration mutate nous convertissons les variables à un format plus approprié, en group_by nous choisissons quelle variable va faire le regroupement et summarise nous créons des nouvelles variables que nous voulons .

df_grouped ressemble à ceci:

# A tibble: 3 × 2 
    year tot_cases 
    <dbl>  <dbl> 
1 2013   6 
2 2014   6 
3 2015   9 
+0

Notez que le résultat de votre solution n'est pas correct. La colonne 'cases' dans' df' est un facteur. Appeler 'as.numeric' ne créera pas un nombre correct, mais donnera l'identifiant de catégorie sous-jacent du niveau factoriel. Vous devez appeler 'as.numeric (as.character())' pour garantir le bon résultat. Voir ma réponse pour la bonne solution. En outre, vous manquez 2015 dans la sortie que vous avez publiée. –

1

Je pense que les solutions basées sur cut sont un peu exagéré. Vous pouvez utiliser la fonction year du paquet lubridate pour extraire l'année de la date:

library(dplyr) 
library(lubridate) 
df %>% mutate(year = year(dates)) 
#  dates cases year 
# 1 2013-01-01  3 2013 
# 2 2013-02-01  5 2013 
# 3 2014-01-01  2 2014 
# 4 2014-02-01  6 2014 
# 5 2015-01-01  8 2015 
# 6 2015-02-01  4 2015 

lubridate est un tel paquet impressionnant en matière de traitement des données en temps. Après la construction de la colonne year, vous pouvez appliquer toutes sortes de résumés. J'utilise le style de dplyr ici:

# Note that as.numeric(as.character()) is needed as `cbind` forces `cases` to be a factor 
df %>% mutate(year = year(dates), cases = as.numeric(as.character(cases))) %>% 
    group_by(year) %>% summarise(tot_cases = sum(cases)) 
# # A tibble: 3 × 2 
# year tot_cases 
# <dbl>  <dbl> 
# 1 2013   8 
# 2 2014   8 
# 3 2015  12 

Notez que group_by assure que toutes les opérations après sont effectuées par catégorie unique, il dit, dans ce cas par an.