日期时间解析异常:无法解析文本'2019-06-07 12:18:16'



我有以下代码将即时转换为字符串,然后将其转换回I

String timestampString = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd hh:mm:ss"));
LOGGER.info("timestampString: " + timestampString);
Instant instant =
LocalDateTime.parse(timestampString,
DateTimeFormatter.ofPattern("yyyy-MM-dd hh:mm:ss")).toInstant(ZoneOffset.UTC);

它将时间戳字符串打印为:2019-06-07 12:45:57

并且在解析字符串时失败:

java.time.format.DateTimeParseException: Text '2019-06-07 12:45:57' could not be parsed: Unable to obtain LocalDateTime from TemporalAccessor: {MinuteOfHour=45, HourOfAmPm=0, NanoOfSecond=0, SecondOfMinute=57, MilliOfSecond=0, MicroOfSecond=0},ISO resolved to 2019-06-07 of type java.time.format.Parsed

为什么即使这与我将时间戳转换为的格式相同,它也无法解析它?

使用 HH 表示一天中的小时而不是 hh

您询问的问题是您在格式模式字符串中使用小写hh(两次)。您需要从 00 到 23 的小时日大写HHhh是上午或下午 01 点到 12 点内的小时。所以出了什么问题,java.time 不知道你的字符串中的12指的是上午 12 点还是下午 12 点,并拒绝为你做出猜测。

如果您仔细阅读异常消息,您还会注意到它说HourOfAmPm=0已解析。它没有说HourOfDay.

DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
String timestampString = LocalDateTime.now().format(formatter);
System.out.println("timestampString: " + timestampString);
Instant instant = LocalDateTime.parse(timestampString, formatter)
.toInstant(ZoneOffset.UTC);
System.out.println("instant: " + instant);

当我刚才运行这个代码片段时,我得到了这个输出:

timestampString: 2019-06-08 19:22:51
instant: 2019-06-08T19:22:51Z

这是错误的!我在 UTC 时间 17:22 左右运行了代码片段,而不是 19:22。由于丹麦仍在使用夏令时(该死),这里的当地时间是 19:22,用于结果并转换为 UTC 的相同挂钟时间,而不是同一时刻。您应该始终将所需的时区传递给now方法以避免此类错误。既然你想要UTC:

String timestampString = LocalDateTime.now(ZoneOffset.UTC).format(formatter);
timestampString: 2019-06-08 17:27:57
instant: 2019-06-08T17:27:57Z

更好的是,不要用LocalDateTime来保存你想用作时刻的东西。请改用InstantOffsetDateTimeZonedDateTime

有关使用hhHHkk格式化和解析小时值的更多信息,请参阅此问题及其答案:SimpleDateFormat 上的 java HH:mm 和 hh:mm 之间的区别。问题是关于臭名昭著的麻烦SimpleDateFormat,但答案对DateTimeFormatter也是有效的。

最新更新