Java 8 - 使用ZonedDateTime的DateTimeFormatter和ISO_INSTANT问题 [英] Java 8 - DateTimeFormatter and ISO_INSTANT issues with ZonedDateTime

查看:2364
本文介绍了Java 8 - 使用ZonedDateTime的DateTimeFormatter和ISO_INSTANT问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以我希望这个代码能够在新的Java 8日期/时间包下工作,因为它只是将给定的ZonedDateTime转换为字符串并使用相同的内置DateTimeFormatter实例(ISO_INSTANT)返回:

So I would expect this code to work under the new Java 8 date/time package since all it does is to convert a given ZonedDateTime to string and back using the same built-in DateTimeFormatter instance (ISO_INSTANT):

ZonedDateTime now = ZonedDateTime.now();
System.out.println(ZonedDateTime.parse(
    now.format(DateTimeFormatter.ISO_INSTANT),
    DateTimeFormatter.ISO_INSTANT));

但显然它没有:

Exception in thread "main" java.time.format.DateTimeParseException: Text '2014-09-01T19:37:48.549Z' could not be parsed: Unable to obtain ZonedDateTime from TemporalAccessor: {MilliOfSecond=549, NanoOfSecond=549000000, MicroOfSecond=549000, InstantSeconds=1409600268},ISO of type java.time.format.Parsed
    at java.time.format.DateTimeFormatter.createError(DateTimeFormatter.java:1918)
    at java.time.format.DateTimeFormatter.parse(DateTimeFormatter.java:1853)
    at java.time.ZonedDateTime.parse(ZonedDateTime.java:597)

我已经看过这个条目,但它没有帮助我,因为需要一个ZonedDateTime对象而不是本地对象,还因为我已经安装了8u20 :无法获取ZonedDateTime fr om使用Java 8中的DateTimeFormatter和ZonedDateTime的TemporalAccessor

I have seen this entry already, but it didn't help me because a need a ZonedDateTime object and not a local one and also because I already have 8u20 installed: Unable to obtain ZonedDateTime from TemporalAccessor using DateTimeFormatter and ZonedDateTime in Java 8

任何人都知道这里发生了什么?

Anyone have any idea what's happening here?

推荐答案

记录 ISO_INSTANT 格式化程序这里 - 这是一个特殊的格式化程序,旨在允许人类可读的Instant形式。因此,此格式化程序适用于 Instant 而不是 ZonedDateTime

The ISO_INSTANT formatter is documented here - "This is a special case formatter intended to allow a human readable form of an Instant". As such, this formatter is intended for use with an Instant not a ZonedDateTime.

格式化时, ISO_INSTANT 可以格式化任何可提供<$ $的时态对象c $ c> ChronoField.INSTANT_SECONDS 和 ChronoField.NANO_OF_SECOND Instant ZonedDateTime 都可以提供这两个字段,因此两者都有效:

When formatting, ISO_INSTANT can format any temporal object that can provide ChronoField.INSTANT_SECONDS and ChronoField.NANO_OF_SECOND. Both Instant and ZonedDateTime can provide these two fields, thus both work:

// works with Instant
Instant instant = Instant.now();
System.out.println(DateTimeFormatter.ISO_INSTANT.format(instant));

// works with ZonedDateTime 
ZonedDateTime zdt = ZonedDateTime.now();
System.out.println(zdt.format(DateTimeFormatter.ISO_INSTANT));

// example output
2014-09-02T08:05:23.653Z



解析



解析时, ISO_INSTANT 只会产生 ChronoField.INSTANT_SECONDS ChronoField.NANO_OF_SECOND 。可以从这两个字段构建 Instant ,但 ZonedDateTime 需要 ZoneId 以及:

Parsing

When parsing, ISO_INSTANT will only produce ChronoField.INSTANT_SECONDS and ChronoField.NANO_OF_SECOND. An Instant can be built from those two fields, but ZonedDateTime requires a ZoneId as well:

要解析 ZonedDateTime ,时区<$ c必不可少$ c> ZoneId 存在。时区可以是(a)从字符串解析,或(b)指定格式化程序(使用JDK 8u20):

To parse a ZonedDateTime it is essential that a time-zone ZoneId is present. The time-zone can be (a) parsed from the string, or (b) specified to the formatter (using JDK 8u20):

// option a - parsed from the string
DateTimeFormatter f = DateTimeFormatter.ISO_DATE_TIME;
ZonedDateTime zdt = ZonedDateTime.parse("2014-09-02T08:05:23.653Z", f);

// option b - specified in the formatter - REQUIRES JDK 8u20 !!!
DateTimeFormatter f = DateTimeFormatter.ISO_INSTANT.withZone(ZoneId.systemDefault());
ZonedDateTime zdt = ZonedDateTime.parse("2014-09-02T08:05:23.653Z", f);

请参阅 ISO_ZONED_DATE_TIME ISO_OFFSET_DATE_TIME ISO_DATE_TIME (这三个中的任何一个都可用于解析 ZonedDateTime 而无需指定 withZone())。

See documentation for ISO_ZONED_DATE_TIME, ISO_OFFSET_DATE_TIME and ISO_DATE_TIME (any of these three can be used to parse a ZonedDateTime without specifying withZone()).

ISO_INSTANT formatter是一种特殊情况格式化程序,设计用于 Instant 。如果您使用 ZonedDateTime ,则应使用其他格式化程序,例如 ISO_DATE_TIME ISO_ZONED_DATE_TIME

The ISO_INSTANT formatter is a special case formatter designed to work with Instant. If you are using a ZonedDateTime you should use a different formatter, such as ISO_DATE_TIME or ISO_ZONED_DATE_TIME.

这篇关于Java 8 - 使用ZonedDateTime的DateTimeFormatter和ISO_INSTANT问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆