【问题标题】:Why is java 8 time not showing me the correct time for timezone Etc/GMT+1为什么 java 8 时间没有向我显示时区 Etc/GMT+1 的正确时间
【发布时间】:2019-11-13 07:10:24
【问题描述】:
ZonedDateTime now = ZonedDateTime.now(ZoneId.of("Etc/GMT+1"));

调试时这个值显示 2019-07-02T14:23:57.463-01:00[Etc/GMT+1]

应该是 16:23,我错过了什么......时钟由于某种原因慢了 2 小时?

【问题讨论】:

  • 提示:"Etc/GMT+1" 与 "UTC-01" 相同(反符号)。您最好使用 UTC 表示法。
  • ... 可以在值中看到:-01:00 vs [Etc/GMT+1](反符号)

标签: java java-8 timestamp java-time


【解决方案1】:

tl;博士

使用时区而不是单纯的偏移量。

ZonedDateTime.now( 
    ZoneId.of( "Europe/Dublin" )
)

详情

在现代协议中,偏移量中的小时-分钟-秒数被视为在基线 (GMT/UTC) 之前 的正数,而在之后 被视为负数 基线。一些较旧的协议则相反。你的Etc/GMT+1 好像是反风格的。

最好的解决方案是使用时区,而不是仅仅使用偏移量。偏移量只是几个小时-分钟-秒。时区更多。时区是特定地区的人们使用的偏移量的过去、现在和未来变化的历史。

时区的名称格式为Continent/Region。例如,America/MontrealEurope/ParisPacific/Auckland

ZoneId z = ZoneId.of( "Europe/Dublin" ) ;
ZonedDateTime zdt = ZonedDateTime.now( z ) ;

生成标准 ISO 8601 格式的字符串,明智地扩展以将区域名称附加在方括号中。

String output = zdt.toString() ;

您的大部分业务逻辑、日志记录和数据更改都应该使用 UTC。要适应 UTC,请从您的 ZonedDateTime 中提取 Instant。同一时刻,时间轴上的同一点,但挂钟时间不同。

Instant instant = zdt.toInstant() ;

生成标准 ISO 8601 格式的字符串。

String output = instant.toString() ;

你的例子

所以现在我们可以回去检查您的具体情况。

让我们使用[Etc/GMT+1] 作为区域名称来解析您的给定字符串。

String input = "2019-07-02T14:23:57.463-01:00[Etc/GMT+1]" ;
ZonedDateTime zdtInput = ZonedDateTime.parse ( input );

然后调整到 UTC。

Instant instant = zdtInput.toInstant ();

再次调整为Europe/Dublin

ZoneId zDublin = ZoneId.of( "Europe/Dublin");
ZonedDateTime zdtDublin = zdtInput.withZoneSameInstant ( zDublin );

转储到控制台。

System.out.println ("zdtInput: " + zdtInput );
System.out.println ("instant: " + instant );
System.out.println ("zdtDublin: " + zdtDublin );

看到这个code run live at IdeOne.com

zdt输入:2019-07-02T14:23:57.463-01:00[Etc/GMT+1]

即时:2019-07-02T15:23:57.463Z

zdt都柏林:2019-07-02T16:23:57.463+01:00[欧洲/都柏林]

14 小时

果然,我们看到[Etc/GMT+1] 的日期比世界标准时间落后一小时(小时偏移的旧反向含义)和14 的一小时。

15 小时

UTC(零时分秒的偏移量)有一小时为15

16 小时

当时Dublin time zone 使用的是爱尔兰标准时间 (IST),UTC +1 而不是 Daylight Saving Time (DST)。所以我们在16 看到它的小时,比UTC 的15 小时提前一个小时。

至关重要:了解所有这三个都代表同一个时刻,时间轴上的同一个点。他们的挂钟时间不同:查看同一时刻的三种方式。


顺便说一句,当您想专门使用偏移量而不是时区时,请使用 OffsetDateTimeZoneOffset 类。 ZonedDateTimeZoneId 类用于时区。

【讨论】:

    猜你喜欢
    • 2019-04-04
    • 2020-10-11
    • 2017-08-31
    • 1970-01-01
    • 2023-03-26
    • 2018-09-29
    • 1970-01-01
    • 2019-09-07
    • 2018-02-05
    相关资源
    最近更新 更多