J'ai une série temporelle horaire de datetimes formatée comme "% Y-% m-% d% H:% M:% S" et comme classe "caractère". Le but est de convertir les données de caractères en date et heure en utilisant as.POSIXct. Cependant, certains enregistrements de la série chronologique n'ont pas la partie temporelle ("% H:% M:% S"), bien que le nombre d'enregistrements par date (24) soit correct.
Est-il possible de renseigner l'heure partie de ces enregistrements avec une séquence d'heures commençant par 00:00:00 et se terminant par 23:00:00 pour chaque date?
Ensemble de données d'origine:
X metadata.id metadata.name metadata.lat metadata.lon Date_time data.v data.s data.f 1 1 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 01:00:00 NA NA 1,1 2 2 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 02:00:00 NA NA 1,1 3 3 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 03:00:00 NA NA 1,1 4 4 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 04:00:00 NA NA 1,1 5 5 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 05:00:00 NA NA 1,1 6 6 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 06:00:00 NA NA 1,1 7 7 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 07:00:00 NA NA 1,1 8 8 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 08:00:00 NA NA 1,1 9 9 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 09:00:00 NA NA 1,1 10 10 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 10:00:00 NA NA 1,1 11 11 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 11:00:00 NA NA 1,1 12 12 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 12:00:00 NA NA 1,1 13 13 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 13:00:00 NA NA 1,1 14 14 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 14:00:00 NA NA 1,1 15 15 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 15:00:00 NA NA 1,1 16 16 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 16:00:00 NA NA 1,1 17 17 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 17:00:00 NA NA 1,1 18 18 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 18:00:00 NA NA 1,1 19 19 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 19:00:00 NA NA 1,1 20 20 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 20:00:00 NA NA 1,1 21 21 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 21:00:00 NA NA 1,1 22 22 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 22:00:00 NA NA 1,1 23 23 9411340 Santa Barbara 34.4031 -119.6928 1990-10-22 23:00:00 NA NA 1,1 24 24 9411340 Santa Barbara 34.4031 -119.6928 1990-10-23 00:00:00 NA NA 1,1 25 25 9411340 Santa Barbara 34.4031 -119.6928 1990-10-23 01:00:00 NA NA 1,1
Ce que je veux:
Date_time ... 1991-03-31 21:00:00 1991-03-31 22:00:00 1991-03-31 23:00:00 1991-04-01 16:00:00 1991-04-01 17:00:00 1991-04-01 18:00:00 ...
Le plus proche que j'ai obtenu est une solution de contournement tout en étant toujours au format caractère, mais le résultat commence à 16:00:00. Veuillez envoyer halp.
hours=c("00:00:00", "01:00:00", "02:00:00", "03:00:00", "04:00:00", "05:00:00", "06:00:00", "07:00:00", "08:00:00", "09:00:00", "10:00:00", "11:00:00", "12:00:00","13:00:00", "14:00:00", "15:00:00", "16:00:00", "17:00:00", "18:00:00", "19:00:00", "20:00:00","21:00:00", "22:00:00", "23:00:00") Dataset %>% mutate(Date_time_filled = ifelse(nchar(as.character(Date_time))<19, paste(Date_time, hours), paste(Date_time)))
Ce que j'ai (mal):
Date_time ... 1991-03-31 21:00:00 1991-03-31 22:00:00 1991-03-31 23:00:00 1991-04-01 00:00:00 1991-04-01 01:00:00 1991-04-01 02:00:00 ...
MODIFIER:
Date_time ... 1991-03-31 21:00:00 1991-03-31 22:00:00 1991-03-31 23:00:00 1991-04-01 1991-04-01 1991-04-01 ...
3 Réponses :
Je ne sais pas si c'est ce que vous recherchez, ou du moins cela peut vous mettre sur la bonne voie:
Dataset$date_time_filled <- seq(as.POSIXct(Dataset$date_time[1]), as.POSIXct(Dataset$date_time[nrow(Dataset)]), by = "1 hour")
Cela pourrait être utilisé comme ceci:
# This is the working horse: seq(as.POSIXct("1991-03-31 00:00:00"), as.POSIXct("1991-04-02 23:00:00"), by = "1 hour") [1] "1991-03-31 00:00:00 -05" "1991-03-31 01:00:00 -05" "1991-03-31 02:00:00 -05" "1991-03-31 03:00:00 -05" "1991-03-31 04:00:00 -05" [6] "1991-03-31 05:00:00 -05" "1991-03-31 06:00:00 -05" "1991-03-31 07:00:00 -05" "1991-03-31 08:00:00 -05" "1991-03-31 09:00:00 -05" [11] "1991-03-31 10:00:00 -05" "1991-03-31 11:00:00 -05" "1991-03-31 12:00:00 -05" "1991-03-31 13:00:00 -05" "1991-03-31 14:00:00 -05" [16] "1991-03-31 15:00:00 -05" "1991-03-31 16:00:00 -05" "1991-03-31 17:00:00 -05" "1991-03-31 18:00:00 -05" "1991-03-31 19:00:00 -05" [21] "1991-03-31 20:00:00 -05" "1991-03-31 21:00:00 -05" "1991-03-31 22:00:00 -05" "1991-03-31 23:00:00 -05" "1991-04-01 00:00:00 -05" [26] "1991-04-01 01:00:00 -05" "1991-04-01 02:00:00 -05" "1991-04-01 03:00:00 -05" "1991-04-01 04:00:00 -05" "1991-04-01 05:00:00 -05" [31] "1991-04-01 06:00:00 -05" "1991-04-01 07:00:00 -05" "1991-04-01 08:00:00 -05" "1991-04-01 09:00:00 -05" "1991-04-01 10:00:00 -05" [36] "1991-04-01 11:00:00 -05" "1991-04-01 12:00:00 -05" "1991-04-01 13:00:00 -05" "1991-04-01 14:00:00 -05" "1991-04-01 15:00:00 -05" [41] "1991-04-01 16:00:00 -05" "1991-04-01 17:00:00 -05" "1991-04-01 18:00:00 -05" "1991-04-01 19:00:00 -05" "1991-04-01 20:00:00 -05" [46] "1991-04-01 21:00:00 -05" "1991-04-01 22:00:00 -05" "1991-04-01 23:00:00 -05" "1991-04-02 00:00:00 -05" "1991-04-02 01:00:00 -05" [51] "1991-04-02 02:00:00 -05" "1991-04-02 03:00:00 -05" "1991-04-02 04:00:00 -05" "1991-04-02 05:00:00 -05" "1991-04-02 06:00:00 -05" [56] "1991-04-02 07:00:00 -05" "1991-04-02 08:00:00 -05" "1991-04-02 09:00:00 -05" "1991-04-02 10:00:00 -05" "1991-04-02 11:00:00 -05" [61] "1991-04-02 12:00:00 -05" "1991-04-02 13:00:00 -05" "1991-04-02 14:00:00 -05" "1991-04-02 15:00:00 -05" "1991-04-02 16:00:00 -05" [66] "1991-04-02 17:00:00 -05" "1991-04-02 18:00:00 -05" "1991-04-02 19:00:00 -05" "1991-04-02 20:00:00 -05" "1991-04-02 21:00:00 -05" [71] "1991-04-02 22:00:00 -05" "1991-04-02 23:00:00 -05"
Dans le cas où la dernière lecture de date_time
manque l'heure, cela fonctionnera, mais considérera la dernière comme si elle avait eu lieu à 00:00:00, donc il peut se tromper en raison de longueurs de vecteur différentes. Que vous devrez probablement ajuster manuellement.
Merci pour ce @PavoDive. Je pense que j'avais des longueurs de vecteur différentes qui compliquaient les choses. Voir ma réponse ci-dessous. Merci encore.
Comme vous avez déjà un certain nombre d'enregistrements présents pour chaque date et que seule la partie heure manque, une approche consiste à utiliser sprintf
et à reproduire la partie heure pour chaque date.
df <- structure(list(Date_time = structure(c(1L, 2L, 3L, 4L, 5L, 6L, 7L, 7L, 7L, 7L, 7L, 7L), .Label = c("1991-03-31 00:00:00", "1991-03-31 01:00:00", "1991-03-31 02:00:00", "1991-03-31 03:00:00", "1991-03-31 04:00:00", "1991-03-31 05:00:00", "1991-04-01"), class = "factor")), class = "data.frame", row.names = c(NA, -12L))
Essayez ceci pendant les heures 0 à 5 sur un petit sous-ensemble.
library(dplyr) df %>% mutate(Date_time1 = as.POSIXct(Date_time), Date_time1 = paste(Date_time1, sprintf("%02d:00:00", 0:5))) # Date_time Date_time1 #1 1991-03-31 00:00:00 1991-03-31 00:00:00 #2 1991-03-31 01:00:00 1991-03-31 01:00:00 #3 1991-03-31 02:00:00 1991-03-31 02:00:00 #4 1991-03-31 03:00:00 1991-03-31 03:00:00 #5 1991-03-31 04:00:00 1991-03-31 04:00:00 #6 1991-03-31 05:00:00 1991-03-31 05:00:00 #7 1991-04-01 1991-04-01 00:00:00 #8 1991-04-01 1991-04-01 01:00:00 #9 1991-04-01 1991-04-01 02:00:00 #10 1991-04-01 1991-04-01 03:00:00 #11 1991-04-01 1991-04-01 04:00:00 #12 1991-04-01 1991-04-01 05:00:00
Vous pouvez exécuter as.POSIXct
sur la colonne Date_time1
pour le convertir en POSIXct
objet.
données
library(dplyr) df %>% mutate(Date_time1 = as.POSIXct(Date_time), Date_time1 = paste(Date_time1, sprintf("%02d:00:00", 0:23)))
J'aime beaucoup cette solution, mais pour une raison quelconque, le premier temps rempli commence toujours à 16:00:00 et non à 00:00:00 lorsque j'essaye de postuler à mes données. Cependant, vos données d'exemple fonctionnent très bien.
@dough Pouvez-vous mettre à jour votre message avec les premières lignes de vos données comme je l'ai fait avec dput
? Faites dput (head (df, 25))
et copiez / collez la sortie dans votre message.
Il en résulte probablement 16h00 au lieu de 00h00 en raison du fuseau horaire dans lequel vous vous trouvez. Utilisez l'argument tz =
dans l'appel à as.POSIXct
. Voir aussi sa page d'aide
@RonakShah J'ai ajouté les premières lignes de mes données réelles.
@PavoDive non, y compris le fuseau horaire, n'a pas aidé. J'ai utilisé Date_time = as.POSIXct ((Date_time), origin = "1970-01-01", tz = "America / Los_Angeles", format = "% Y-% m-% d% H:% M:% S" ). Cependant, je voulais éviter de mettre les données au format date-heure pour l'instant, car cela semble compliquer les choses
Au lieu d'ajouter les temps manquants dans l'ensemble de données de la série chronologique, j'ai fini par devoir revenir aux ensembles de données individuels ne contenant qu'un mois de données. Les mois de données manquantes étaient toujours avril, donc 30 jours. Ensuite, ce qui suit a fonctionné:
#Fix April Datasets missing hour data hours=c("00:00:00", "01:00:00", "02:00:00", "03:00:00", "04:00:00", "05:00:00", "06:00:00", "07:00:00", "08:00:00", "09:00:00", "10:00:00", "11:00:00", "12:00:00","13:00:00", "14:00:00", "15:00:00", "16:00:00", "17:00:00", "18:00:00", "19:00:00", "20:00:00","21:00:00", "22:00:00", "23:00:00") pattern=glob2rx("******04**.csv") #Monthly Dataset MonthlyData_filenames=list.files(path="~/.../Hourly", pattern=pattern, full.names = T) for(i in 1:length(MonthlyData_filenames)){ input = read.csv(MonthlyData_filenames[i], head=TRUE, sep=",") if(nchar(as.character(input$Date_time))>=19){ next } output = input %>% mutate(hour = rep(hours, times=30)) %>% mutate(Date_time = paste(Date_time, hour, sep=" ")) %>% select(-hour) write.csv(output, MonthlyData_filenames[i], row.names=FALSE) }