2013-08-30 20 views
1

您好,我有一個長度爲幾百萬的字符向量(rr),它以澳大利亞/悉尼記錄的格式%Y-%m-%d %H:%M:%S表示時間和日期戳。fastPOSIXct等效於將非UTC轉換爲UTC

如何獲得一個代表這個的POSIXct對象(快速)。

我發現fastPOSIXctfasttime包,但對於本是準確的,它需要原始字符串是在GMT/UTC(其礦是不是),然後使用tz轉換回正確的時區arguement ...

> head(rr) 
[1] "2009-05-01 10:01:00" "2009-05-01 10:02:00" "2009-05-01 10:03:00" "2009-05-01 10:04:00" 
[5] "2009-05-01 10:05:00" "2009-05-01 10:06:00" 

> as.POSIXct(head(rr),tz="Australia/Sydney") 
[1] "2009-05-01 10:01:00 EST" "2009-05-01 10:02:00 EST" "2009-05-01 10:03:00 EST" 
[4] "2009-05-01 10:04:00 EST" "2009-05-01 10:05:00 EST" "2009-05-01 10:06:00 EST" 

上面一行需要年齡,如果這樣做的全套資料...所以任何速度的提高,將不勝感激。謝謝。

+1

由於POSIXct日期時間只是一個基礎數值向量,因此可以使用'fastPOSIXct',然後添加所需的偏移量以將GMT從AEST轉換爲AEST。 –

+0

您將如何製作偏移對象? –

+1

目前這個問題沒有詳細說明。這些時間是否有「夏令時」? –

回答

1

下面是一個方法:

ⅰ)騙fasttime()和假裝的數據是UTC,要用到的數據解析爲一個矢量x

II)計算的使用第一數據點偏移以UTC :

R> d1 <- "2009-05-01 10:01:01" ## or use `head(rr,1)` 
R> t1 <- as.POSIXct(d1,tz="Australia/Sydney") 
R> t2 <- as.POSIXct(d1,tz="UTC") 
R> offset <- as.numeric(difftime(t2, t1, units="secs")) 
R> offset 
[1] 36000 

三)offset值應用到你的數據 - 這是一個快速增加的POSIXct真的是一個數字式帶(分數)秒(自紀元)爲單位。

+0

正如@Ben Bolker的評論所述,只有當記錄的時區不符合夏令時時,這種方法纔有效, GMT/UTC始終是恆定的...我也不太確定'd2'對象是你的代碼的第三行... –

+0

我們通常在一天之內處理幾個100k的數據,因此跨越TZ是通常不是一個問題 - 正如本指出的那樣,一個常見的選擇是解析所有時間字符串,這是昂貴的。 'd2'是一個錯字,應該也是'd1' - 固定的。 –

1

德克的回答這個QN啓發,我做了這個包裝器在全年的處理一大堆日期:

fastPOSIXct_generic <- function(x, mytz = "America/New_York") 
{ 
    # Caution, read: ?DateTimeClasses 
    stopifnot(is.character(x)) 
    times_UTC <- fastPOSIXct(x, tz='UTC') 
    num_times <- as.numeric(times_UTC) 
    t1 <- as.POSIXct(x[1], tz = mytz) 
    t2 <- as.POSIXct(x[1], tz = "UTC") 
    offset <- as.numeric(difftime(t1, t2, units = "secs")) 
    daylightoffset <- as.POSIXlt(t1)$isdst 
    # For this first 'time' in t1 and t2, remove possible impact of losing one hour by setting clocks one hour forward during summer months: 
    offset <- offset + daylightoffset * 3600 
    num_times <- num_times + offset 
    new_num_times <- as.POSIXct(num_times, tz = mytz, origin = '1970-01-01') 
    new_num_times2 <- new_num_times - as.POSIXlt(new_num_times)$isdst * 3600 
    return(new_num_times2) 
} 

# Test Sydney time 

mm <- as.POSIXct(c("2015-03-15 15:00:00", "2015-4-10 15:00:00", "2014-10-01 15:00:00", "2015-10-15 15:00:00"), tz = "Australia/Sydney") 
# "2015-03-15 15:00:00 AEDT" "2015-04-10 15:00:00 AEST" "2014-10-01 15:00:00 AEST" "2015-10-15 15:00:00 AEDT" 
aus_stamps <- as.character(mm) 
aus_back <- fastPOSIXct_generic(x = aus_stamps, mytz = "Australia/Sydney") 
#"2015-03-15 15:00:00 AEDT" "2015-04-10 15:00:00 AEST" "2014-10-01 15:00:00 AEST" "2015-10-15 15:00:00 AEDT" 
identical(mm, aus_back) 
# TRUE 

我的使用情況幾乎總是UTC美國/紐約,在那裏到目前爲止,似乎工作正常。我不知道它是否適用於其他時區;只是dst有一個小時的情況。