【发布时间】:2015-09-09 10:54:08
【问题描述】:
考虑这个 R 代码,它使用定义的时间格式字符串(下面的 timeFormat 变量)来格式化和解析日期:
time = as.POSIXct(1433867059, origin = "1970-01-01")
print(time)
print( as.numeric(time) )
timeFormat = "%Y-%m-%d %H:%M:%OS3"
tz = "EST"
timestamp = format(time, format = timeFormat, tz = tz)
print(timestamp)
timeParsed = as.POSIXct(timestamp, format = timeFormat, tz = tz)
print(timeParsed)
print( as.numeric(timeParsed) )
如果我将其粘贴到运行最新 (3.2.0) 稳定版本的 Windows 机器上的 Rgui 中,我会得到:
> time = as.POSIXct(1433867059, origin = "1970-01-01")
> print(time)
[1] "2015-06-09 12:24:19 EDT"
> print( as.numeric(time) )
[1] 1433867059
>
> timeFormat = "%Y-%m-%d %H:%M:%OS3"
> tz = "EST"
>
> timestamp = format(time, format = timeFormat, tz = tz)
> print(timestamp)
[1] "2015-06-09 11:24:19.000"
>
> timeParsed = as.POSIXct(timestamp, format = timeFormat, tz = tz)
> print(timeParsed)
[1] NA
> print( as.numeric(timeParsed) )
[1] NA
注意以 %OS3 结尾的时间格式如何生成正确的时间戳(3 位数毫秒分辨率)。
但是,相同的时间格式无法将该时间戳解析回原始 POSIXct 值;它会吐出并解析 NA。
有人知道怎么回事吗?
网络搜索发现this stackoverflow link, 其中一位评论者 Waldir Leoncio 在第一个答案中似乎描述了与我所做的 %OS3 相同的解析错误:
"例如使用 strptime(y, "%d.%m.%Y %H:%M:%OS3"),但它没有 为我工作。 Henrik 注意到该函数的帮助页面 ?strptime 指出 %OS3 位是依赖于操作系统的。我正在使用更新的 Ubuntu 13.04 和使用 %OS3 会产生 NA。"
上面引用中提到的帮助页面可能是this link, 不幸的是,这很简洁,只是说
"特定于 R 的是 %OSn,它对于输出给出截断的秒数 到 0
关于 strptime(即解析)的最后一句话很微妙:它说“for strptime %OS”。请注意没有“n”:它说 %OS 而不是 %OSn。
这是否意味着 %OSn 不能用于解析,只能用于格式化?
这是我凭经验发现的,但这是预期的行为还是错误?
非常烦人的行为,因为这意味着我需要不同的时间格式来格式化和解析。以前从未在任何其他语言的日期 API 中看到过这种情况...
(旁白:我知道还有另一个问题,即使您只是想格式化,使用 %OSn:R 会截断小数部分而不是圆形。对于那些不知道这种不良行为的人,讨论了它的危害@987654323 @、here 和 here。)
【问题讨论】:
-
R-3.2.1,而不是 3.2.0,是截至 2015 年 6 月 18 日的当前稳定版本。截断而不是舍入小数秒的“坏”行为是主观的。我敢肯定,如果选择了其他约定,您会发现很多人抱怨 “不良”行为。