尝试反向转换时区向量
Trying to reverse-convert a vector of time zones
我有这个时间戳数据库 (AlertTime),并且我知道它们在哪个时区 (TimeZone)。我知道如何将这些日期设置为 POSIXCT 或者如果它们都是 UTC,但我正在努力将它们标识为它们的本地时间戳,因为大多数函数不接受 tz 的向量。
我确实需要格式正确的本地时间戳 (AlertTimeLocal) 和 UTC 等效时间 (AlertTimeUTC)。
AlertTime TimeZone AlertTimeLocal (desired) AlertTimeUTC (desired)
11 May 2020, 06:22 PM America/Denver 2020-05-11 18:22:00 MDT 2020-05-12 00:22:00 MDT
11 MAY 2020, 04:11 AM America/Los_Angeles 2020-05-11 04:11:00 PDT 2020-05-11 11:11:00 UTC
10 MAY 2020, 03:38 PM America/Chicago 2020-05-10 15:38:00 CDT 2020-05-10 20:38:00 CDT
我正在使用这段代码,但它似乎不再执行任何操作:
FreshAir$AlertTimeLocal <- mapply(function(x,y) {format(x, tz=y, usetz=TRUE)}, FreshAir$AlertTime, FreshAir$TimeZone)
将所有 RAW 时间戳设置为 UTC,然后将它们转换为相反方向的等效时区是否是一个 hacky 解决方案?
我们可以使用 lubridate
中的 force_tzs
library(lubridate)
library(dplyr)
df1 %>%
mutate(AlertTimeLocal = dmy_hm(AlertTime),
AlertTimeUTC = force_tzs(AlertTimeLocal, tzones = TimeZone))
# AlertTime TimeZone AlertTimeLocal AlertTimeUTC
#1 11 May 2020, 06:22 PM America/Denver 2020-05-11 18:22:00 2020-05-12 00:22:00
#2 11 MAY 2020, 04:11 AM America/Los_Angeles 2020-05-11 04:11:00 2020-05-11 11:11:00
#3 10 MAY 2020, 03:38 PM America/Chicago 2020-05-10 15:38:00 2020-05-10 20:38:00
更新
如果我们需要存储为单独的时区,我们可以使用 list
列
library(purrr)
df2 <- df1 %>%
mutate(AlertTime2 = dmy_hm(AlertTime),
AlertTimeUTC = force_tzs(AlertTime2, tzones = TimeZone),
AlertTimeLocal = map2(AlertTime2, TimeZone, ~ force_tz(.x, tzone = .y)))
df2$AlertTimeLocal
#[[1]]
#[1] "2020-05-11 18:22:00 MDT"
#[[2]]
#[1] "2020-05-11 04:11:00 PDT"
#[[3]]
#[1] "2020-05-10 15:38:00 CDT"
数据
df1 <- structure(list(AlertTime = c("11 May 2020, 06:22 PM",
"11 MAY 2020, 04:11 AM",
"10 MAY 2020, 03:38 PM"), TimeZone = c("America/Denver",
"America/Los_Angeles",
"America/Chicago")), class = "data.frame", row.names = c(NA,
-3L))
我认为一个整洁的解决方案可能看起来更干净,但如果你想要一个基本的 R 解决方案,这里有一个使用@akrun 的替代方案 df1
:
df1$AlertTimeLocal <- df1$AlertTimeUTC <-
c.POSIXct(Map(as.POSIXct, df1$AlertTime, tz = df1$TimeZone, format = "%d %b %Y, %I:%M %p"))
attr(df1$AlertTimeUTC, "tzone") <- "UTC"
attr(df1$AlertTimeLocal, "tzone") <- "US/Mountain"
df1
# AlertTime TimeZone AlertTimeUTC AlertTimeLocal
# 1 11 May 2020, 06:22 PM America/Denver 2020-05-12 00:22:00 2020-05-11 18:22:00
# 2 11 MAY 2020, 04:11 AM America/Los_Angeles 2020-05-11 11:11:00 2020-05-11 05:11:00
# 3 10 MAY 2020, 03:38 PM America/Chicago 2020-05-10 20:38:00 2020-05-10 14:38:00
不过,有些事情还没有讨论:在 R 中,POSIXt
的一个向量中不能有不同的时区。也就是说,在向量中,时区是 向量 的属性,而不是元素的属性。如果您在该列中的每个时间都需要单独的时区,则需要做一个列表列。这行得通,但在 data.frame
.
上工作的 utilities/functions 并不总是很好地支持它
我有这个时间戳数据库 (AlertTime),并且我知道它们在哪个时区 (TimeZone)。我知道如何将这些日期设置为 POSIXCT 或者如果它们都是 UTC,但我正在努力将它们标识为它们的本地时间戳,因为大多数函数不接受 tz 的向量。
我确实需要格式正确的本地时间戳 (AlertTimeLocal) 和 UTC 等效时间 (AlertTimeUTC)。
AlertTime TimeZone AlertTimeLocal (desired) AlertTimeUTC (desired)
11 May 2020, 06:22 PM America/Denver 2020-05-11 18:22:00 MDT 2020-05-12 00:22:00 MDT
11 MAY 2020, 04:11 AM America/Los_Angeles 2020-05-11 04:11:00 PDT 2020-05-11 11:11:00 UTC
10 MAY 2020, 03:38 PM America/Chicago 2020-05-10 15:38:00 CDT 2020-05-10 20:38:00 CDT
我正在使用这段代码,但它似乎不再执行任何操作:
FreshAir$AlertTimeLocal <- mapply(function(x,y) {format(x, tz=y, usetz=TRUE)}, FreshAir$AlertTime, FreshAir$TimeZone)
将所有 RAW 时间戳设置为 UTC,然后将它们转换为相反方向的等效时区是否是一个 hacky 解决方案?
我们可以使用 lubridate
force_tzs
library(lubridate)
library(dplyr)
df1 %>%
mutate(AlertTimeLocal = dmy_hm(AlertTime),
AlertTimeUTC = force_tzs(AlertTimeLocal, tzones = TimeZone))
# AlertTime TimeZone AlertTimeLocal AlertTimeUTC
#1 11 May 2020, 06:22 PM America/Denver 2020-05-11 18:22:00 2020-05-12 00:22:00
#2 11 MAY 2020, 04:11 AM America/Los_Angeles 2020-05-11 04:11:00 2020-05-11 11:11:00
#3 10 MAY 2020, 03:38 PM America/Chicago 2020-05-10 15:38:00 2020-05-10 20:38:00
更新
如果我们需要存储为单独的时区,我们可以使用 list
列
library(purrr)
df2 <- df1 %>%
mutate(AlertTime2 = dmy_hm(AlertTime),
AlertTimeUTC = force_tzs(AlertTime2, tzones = TimeZone),
AlertTimeLocal = map2(AlertTime2, TimeZone, ~ force_tz(.x, tzone = .y)))
df2$AlertTimeLocal
#[[1]]
#[1] "2020-05-11 18:22:00 MDT"
#[[2]]
#[1] "2020-05-11 04:11:00 PDT"
#[[3]]
#[1] "2020-05-10 15:38:00 CDT"
数据
df1 <- structure(list(AlertTime = c("11 May 2020, 06:22 PM",
"11 MAY 2020, 04:11 AM",
"10 MAY 2020, 03:38 PM"), TimeZone = c("America/Denver",
"America/Los_Angeles",
"America/Chicago")), class = "data.frame", row.names = c(NA,
-3L))
我认为一个整洁的解决方案可能看起来更干净,但如果你想要一个基本的 R 解决方案,这里有一个使用@akrun 的替代方案 df1
:
df1$AlertTimeLocal <- df1$AlertTimeUTC <-
c.POSIXct(Map(as.POSIXct, df1$AlertTime, tz = df1$TimeZone, format = "%d %b %Y, %I:%M %p"))
attr(df1$AlertTimeUTC, "tzone") <- "UTC"
attr(df1$AlertTimeLocal, "tzone") <- "US/Mountain"
df1
# AlertTime TimeZone AlertTimeUTC AlertTimeLocal
# 1 11 May 2020, 06:22 PM America/Denver 2020-05-12 00:22:00 2020-05-11 18:22:00
# 2 11 MAY 2020, 04:11 AM America/Los_Angeles 2020-05-11 11:11:00 2020-05-11 05:11:00
# 3 10 MAY 2020, 03:38 PM America/Chicago 2020-05-10 20:38:00 2020-05-10 14:38:00
不过,有些事情还没有讨论:在 R 中,POSIXt
的一个向量中不能有不同的时区。也就是说,在向量中,时区是 向量 的属性,而不是元素的属性。如果您在该列中的每个时间都需要单独的时区,则需要做一个列表列。这行得通,但在 data.frame
.