it-swarm.com.de

Jahr und Monat ("JJJJ-mm" Format) in ein Datum umrechnen?

Ich habe einen Datensatz, der so aussieht:

Month    count
2009-01  12
2009-02  310
2009-03  2379
2009-04  234
2009-05  14
2009-08  1
2009-09  34
2009-10  2386

Ich möchte die Daten darstellen (Monate als x-Werte und zählt als y-Werte). Da es Datenlücken gibt, möchte ich die Informationen für den Monat in ein Datum umwandeln. Ich habe es versucht:

as.Date("2009-03", "%Y-%m")

Aber es hat nicht funktioniert. Was ist falsch? Es scheint, dass as.Date () auch einen Tag benötigt und keinen Standardwert für den Tag festlegen kann. Welche Funktion löst mein Problem?

72
R_User

Versuche dies. (Hier verwenden wir text=Lines, um das Beispiel in sich zu halten, aber in Wirklichkeit würden wir es durch den Dateinamen ersetzen.)

Lines <- "2009-01  12
2009-02  310
2009-03  2379
2009-04  234
2009-05  14
2009-08  1
2009-09  34
2009-10  2386"

library(Zoo)
z <- read.Zoo(text = Lines, FUN = as.yearmon)
plot(z)

Die X-Achse ist mit diesen Daten nicht so hübsch, aber wenn Sie mehr Daten in der Realität haben, können sie in Ordnung sein oder Sie können den Code für eine ausgefallene X-Achse verwenden, die im Beispielabschnitt von ?plot.Zoo gezeigt wird.

Die Zoo-Serie z, die oben erstellt wurde, hat einen "yearmon"-Zeitindex und sieht folgendermaßen aus:

> z
Jan 2009 Feb 2009 Mar 2009 Apr 2009 May 2009 Aug 2009 Sep 2009 Oct 2009 
      12      310     2379      234       14        1       34     2386 

"yearmon" kann auch alleine verwendet werden:

> as.yearmon("2000-03")
[1] "Mar 2000"

Hinweis:

  1. "yearmon" Klassenobjekte werden in der Kalenderreihenfolge sortiert.

  2. Dadurch werden die monatlichen Punkte in gleichmäßigen Abständen aufgezeichnet, was wahrscheinlich erwünscht ist. Wenn Sie jedoch die Punkte in ungleichmäßigen Abständen im Abstand von der Anzahl der Tage in jedem Monat darstellen möchten, konvertieren Sie den Index von z in die Klasse "Date": time(z) <- as.Date(time(z)).

50
G. Grothendieck

Da Datumsangaben einem numerischen Wert und einem Startdatum entsprechen, benötigen Sie tatsächlich den Tag. Wenn Sie wirklich benötigen, dass Ihre Daten im Datumsformat vorliegen, können Sie den Tag manuell auf den ersten jedes Monats festlegen, indem Sie ihn an dem Datum einfügen:

month <- "2009-03"
as.Date(paste(month,"-01",sep=""))
59
Sacha Epskamp

Die prägnanteste Lösung, wenn Sie die Datumsangaben im Datumsformat benötigen:

library(Zoo)
month <- "2000-03"
as.Date(as.yearmon(month))
[1] "2000-03-01"

as.Date legt den ersten Tag jedes Monats für Sie auf ein yearmon-Objekt fest. 

23
Ben Rollert

Sie können dies auch mit den Funktionen parse_date_time oder fast_strptime aus dem Paket lubridate- erreichen:

> parse_date_time(dates1, "ym")
[1] "2009-01-01 UTC" "2009-02-01 UTC" "2009-03-01 UTC"

> fast_strptime(dates1, "%Y-%m")
[1] "2009-01-01 UTC" "2009-02-01 UTC" "2009-03-01 UTC"

Der Unterschied zwischen diesen beiden besteht darin, dass parse_date_time Formatspezifikationen im Lubridate-Stil zulässt, während fast_strptime dieselbe Formatangabe wie strptime erfordert.

Zur Angabe der Zeitzone können Sie den Parameter tz- verwenden:

> parse_date_time(dates1, "ym", tz = "CET")
[1] "2009-01-01 CET" "2009-02-01 CET" "2009-03-01 CET"

Wenn Sie Unregelmäßigkeiten in Ihren Datum-Uhrzeit-Daten haben, können Sie mit dem Parameter truncated- angeben, wie viele Unregelmäßigkeiten zulässig sind:

> parse_date_time(dates2, "ymdHMS", truncated = 3)
[1] "2012-06-01 12:23:00 UTC" "2012-06-01 12:00:00 UTC" "2012-06-01 00:00:00 UTC"

Verwendete Daten:

dates1 <- c("2009-01","2009-02","2009-03")
dates2 <- c("2012-06-01 12:23","2012-06-01 12",'2012-06-01")
12
Jaap

Verwenden Sie anytime package:

library(anytime)

anydate("2009-01")
# [1] "2009-01-01"
10
zx8754

Um die Zeichenfolge in ein Datum umzuwandeln, benötigen Sie, wie oben (und anderswo in SO) erwähnt, ein bestimmtes Datum des Monats. Auf der as.Date()-Manualseite:

Wenn die Datumszeichenfolge das Datum nicht vollständig angibt, ist die zurückgegebene Antwort möglicherweise systemspezifisch. Am häufigsten wird davon ausgegangen, dass ein fehlendes Jahr, ein Monat oder ein Tag das aktuelle ist. Wenn ein Datum falsch angegeben wird, wird bei zuverlässigen Implementierungen ein Fehler ausgegeben, und das Datum wird als NA gemeldet. Leider sind einige gängige Implementierungen (wie glibc) unzuverlässig und erraten die beabsichtigte Bedeutung.

Eine einfache Lösung wäre, das Datum "01" in jedes Datum einzufügen und strptime() als ersten Tag des Monats anzugeben.


Für diejenigen, die etwas mehr Hintergrundinformationen zu Datums- und Zeitangaben in R suchen:

Verwenden Sie in R Zeiten POSIXct und POSIXlt Klassen und Datumsangaben die Date Klasse.

Datumsangaben werden als Anzahl von Tagen seit dem 1. Januar 1970 und Zeiten als Anzahl von Sekunden seit dem 1. Januar 1970 gespeichert.

Also zum Beispiel:

d <- as.Date("1971-01-01")
unclass(d)  # one year after 1970-01-01
# [1] 365

pct <- Sys.time()  # in POSIXct
unclass(pct)  # number of seconds since 1970-01-01
# [1] 1450276559
plt <- as.POSIXlt(pct)
up <- unclass(plt)  # up is now a list containing the components of time
names(up)
# [1] "sec"    "min"    "hour"   "mday"   "mon"    "year"   "wday"   "yday"   "isdst"  "zone"  
# [11] "gmtoff"
up$hour
# [1] 9

So führen Sie Vorgänge an Datum und Uhrzeit durch:

plt - as.POSIXlt(d)
# Time difference of 16420.61 days

Und um Datumsangaben zu verarbeiten, können Sie strptime() verwenden (diese Beispiele können Sie von der Manpage ausleihen):

strptime("20/2/06 11:16:16.683", "%d/%m/%y %H:%M:%OS")
# [1] "2006-02-20 11:16:16 EST"

# And in vectorized form:
dates <- c("1jan1960", "2jan1960", "31mar1960", "30jul1960")
strptime(dates, "%d%b%Y")
# [1] "1960-01-01 EST" "1960-01-02 EST" "1960-03-31 EST" "1960-07-30 EDT"
4
Megatron

Ich denke, die Lösung von @ ben-rollert ist eine gute Lösung. 

Sie müssen nur vorsichtig sein, wenn Sie diese Lösung in einer Funktion innerhalb eines neuen Pakets verwenden möchten. 

Bei der Entwicklung von Paketen wird empfohlen, die Syntax packagename::function_name() zu verwenden (siehe http://kbroman.org/pkg_primer/pages/depends.html ). 

In diesem Fall müssen Sie die Version von as.Date() verwenden, die in der Zoo-Bibliothek definiert ist. 

Hier ist ein Beispiel : 

> devtools::session_info()
Session info ----------------------------------------------------------------------------------------------------------------------------------------------------
 setting  value                       
 version  R version 3.3.1 (2016-06-21)
 system   x86_64, linux-gnu           
 ui       RStudio (1.0.35)            
 language (EN)                        
 collate  C                           
 tz       <NA>                        
 date     2016-11-09                  

Packages --------------------------------------------------------------------------------------------------------------------------------------------------------

 package  * version date       source        
 devtools   1.12.0  2016-06-24 CRAN (R 3.3.1)
 digest     0.6.10  2016-08-02 CRAN (R 3.2.3)
 memoise    1.0.0   2016-01-29 CRAN (R 3.2.3)
 withr      1.0.2   2016-06-20 CRAN (R 3.2.3)

> as.Date(Zoo::as.yearmon("1989-10", "%Y-%m")) 
Error in as.Date.default(Zoo::as.yearmon("1989-10", "%Y-%m")) : 
  do not know how to convert 'Zoo::as.yearmon("1989-10", "%Y-%m")' to class “Date”

> Zoo::as.Date(Zoo::as.yearmon("1989-10", "%Y-%m"))
[1] "1989-10-01"

Wenn Sie also ein Paket entwickeln, sollten Sie Folgendes anwenden: 

Zoo::as.Date(Zoo::as.yearmon("1989-10", "%Y-%m"))
0
PAC