我有SimpleDateFormat构造函数为

SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'")

我正在解析字符串“2013-09-29T18:46:19Z”。

我读到这里Z表示GMT/UTC时区。但是当我在控制台打印这个日期时,它为返回的日期打印IST时区。

现在我的问题是我的输出是对的还是错的?


当前回答

博士tl;

其他答案在Java 8中已经过时了。

Instant                           // Represent a moment in UTC. 
.parse( "2013-09-29T18:46:19Z" )  // Parse text in standard ISO 8601 format where the `Z` means UTC, pronounces “Zulu”.
.atZone(                          // Adjust from UTC to a time zone. 
    ZoneId.of( "Asia/Kolkata" )
)                                 // Returns a `ZonedDateTime` object. 

ISO 8601

您的字符串格式恰好符合ISO 8601标准。该标准定义了将各种日期-时间值表示为文本的合理格式。

java.time

旧的java.util.Date/。Calendar和java.text. simpledateformat类已被java.text. simpledateformat类所取代。在Java 8及以后版本中内置了时间框架。看教程。避免使用旧的类,因为它们已被证明是设计糟糕、令人困惑和麻烦的。

旧类中的部分糟糕设计让您感到困扰,其中toString方法在生成日期-时间值的文本表示时应用JVM的当前默认时区,而该日期-时间值实际上是UTC (GMT);善意但令人困惑。

java。时间类在解析/生成日期-时间值的文本表示时默认使用ISO 8601格式。因此不需要指定解析模式。

一个瞬间是UTC时间轴上的一个时刻。

Instant instant = Instant.parse( "2013-09-29T18:46:19Z" );

您可以根据需要应用时区来生成一个zoneeddatetime对象。

ZoneId zoneId = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = instant.atZone( zoneId );

其他回答

“T”和“Z”在这里被认为是常数。你需要传递不带引号的Z。此外,您需要在输入字符串中指定时区。

例如:2013-09-29T18:46:19-0700 格式为"yyyy-MM-dd 'HH:mm:ssZ"

你没有设置时区,只是在日期/时间的末尾添加了一个Z,所以它看起来像一个GMT日期/时间,但这不会改变值。

将时区设置为GMT,将是正确的。

SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'");
sdf.setTimeZone(TimeZone.getTimeZone("GMT"));

如果你没有选择去java8更好的使用 'yyyy-MM-dd' t ' hh:mm:ssXXX',因为这将再次被正确解析(而只有一个X可能不是这种情况……取决于你的解析函数)

X生成:+01

XXX生成:+01:00

博士tl;

其他答案在Java 8中已经过时了。

Instant                           // Represent a moment in UTC. 
.parse( "2013-09-29T18:46:19Z" )  // Parse text in standard ISO 8601 format where the `Z` means UTC, pronounces “Zulu”.
.atZone(                          // Adjust from UTC to a time zone. 
    ZoneId.of( "Asia/Kolkata" )
)                                 // Returns a `ZonedDateTime` object. 

ISO 8601

您的字符串格式恰好符合ISO 8601标准。该标准定义了将各种日期-时间值表示为文本的合理格式。

java.time

旧的java.util.Date/。Calendar和java.text. simpledateformat类已被java.text. simpledateformat类所取代。在Java 8及以后版本中内置了时间框架。看教程。避免使用旧的类,因为它们已被证明是设计糟糕、令人困惑和麻烦的。

旧类中的部分糟糕设计让您感到困扰,其中toString方法在生成日期-时间值的文本表示时应用JVM的当前默认时区,而该日期-时间值实际上是UTC (GMT);善意但令人困惑。

java。时间类在解析/生成日期-时间值的文本表示时默认使用ISO 8601格式。因此不需要指定解析模式。

一个瞬间是UTC时间轴上的一个时刻。

Instant instant = Instant.parse( "2013-09-29T18:46:19Z" );

您可以根据需要应用时区来生成一个zoneeddatetime对象。

ZoneId zoneId = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = instant.atZone( zoneId );

现有格式化程序的参考示例:

String date1 = "2022-06-19T01:26:05.000+00:00"; 
// internally using DateTimeFormatter.ISO_OFFSET_DATE_TIME
System.out.println(OffsetDateTime.parse(date1));

//internally using DateTimeFormatter.ISO_ZONED_DATE_TIME
System.out.println(ZonedDateTime.parse(date1));

String date2 = "2022-06-19T01:26:05"; 
//internally using DateTimeFormatter.ISO_LOCAL_DATE_TIME)
System.out.println(LocalDateTime.parse(date2)); 

String date3 = "2022-06-19T01:26:05.00Z"; 
//internally using DateTimeFormatter.ISO_INSTANT
System.out.println(Instant.parse(date3));

输出:

2022-06-19T01:26:05Z
2022-06-19T01:26:05Z
2022-06-19T01:26:05
2022-06-19T01:26:05Z