2 回答
TA贡献1798条经验 获得超7个赞
LocalDateTime从ZonedDateTime时区的简单切割中获取。它的价值无关紧要。您需要做的是将您的ZonedDateTime区域从+8 区转换为+2 区,这将相应地改变时间。然后就可以LocalDateTime从你的修改中ZonedDateTime得到想要的效果了。这是一个演示它的示例:
private static void testDateParsing() {
ZonedDateTime zdt = ZonedDateTime.parse("2019-08-28T10:39:57+08:00", DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ssZZZZZ"));
ZonedDateTime modifiedZdt = zdt.withZoneSameInstant(ZoneId.systemDefault());
System.out.println(zdt);
System.out.println(modifiedZdt);
System.out.println(LocalDateTime.from(zdt));
System.out.println(LocalDateTime.from(modifiedZdt));
}
输出是:
2019-08-28T10:39:57+08:00
2019-08-28T05:39:57+03:00[Asia/Jerusalem]
2019-08-28T10:39:57
2019-08-28T05:39:57
请注意,我的本地时区是+03,而不是您的+02。
TA贡献1785条经验 获得超8个赞
String text = "2019-08-28T10:39:57+02:00";
OffsetDateTime time = OffsetDateTime.parse(text);
System.out.println("Hour of day is " + time.getHour());
输出是(如您所料):
一天中的小时是 10
尝试不同的偏移量:
String text = "2019-08-28T10:39:57+08:00";
一天中的小时是 10
所以仍然相同,仍然是字符串中给出的小时。这就是 10 的由来。我从你的代码中选择了一个稍微简单的代码示例,但它演示的行为与你的代码相同,没有区别,也足以解释。
需要注意的一点是,代码不依赖于 JVM 的时区设置(您报告为欧洲/巴黎)。那挺好的。这意味着,如果我们相信代码是正确的,我们也可以相信它能够在所有时区的所有 JVM 上正确运行。
LocalDateTime在您的代码中,您通过调用转换为toLocalDateTime(). 通常这种转换没有任何充分的理由,因为OffsetDateTime或ZonedDateTime很好地实现了目的。OffsetDateTime转换的作用是保留或中的日期和时间(挂钟时间)ZonedDateTime并丢弃偏移量或时区信息。因此,如果一天中的小时在转换前为 10,则转换后也将为 10。如果您期望转换为当地时间(欧洲/巴黎),您可能会感到困惑。不执行此类转换。Local在 java.time 名称中意味着:没有时区或偏移量。有人认为该词的使用Local因为这个含义具有误导性(从某种意义上说,它是历史性的,因为它是从 java.time 的先驱 Joda-Time 接管的)。
那么解析 RFC 3339 字符串(表示嵌入偏移中的瞬间)并将其转换为 LocalDateTime可能的区域调整对象的正确方法是什么?假设机器在 CE[S]T 时区运行。
解析已经可以正确地为您工作。您可能不需要转换。可以直接比较。和的和方法在isBefore比较时会考虑不同的偏移量或时区,并将为您提供所需的结果。如果您确实想转换:isEqualisAfterOffsetDateTimeZonedDateTime
String text = "2019-08-28T10:39:57+08:00";
OffsetDateTime time = OffsetDateTime.parse(text);
System.out.println("Hour of day is " + time.getHour());
ZoneId myTimeZone = ZoneId.of("Europe/Paris");
ZonedDateTime timeInFrance = time.atZoneSameInstant(myTimeZone);
System.out.println("Hour of day in France is " + timeInFrance.getHour());
Hour of day is 10
Hour of day in France is 4
同样,您可以转换为LocalDateTime并保留 4 点,但我不明白您为什么应该这样做。
关于我对代码的简化:您的 RFC 3339 字符串包含与 UTC (+02:00) 的偏移量,而不是时区(如欧洲/巴黎或欧洲/罗马)。所以用ZonedDateTime它来解析就有点矫枉过正了;OffsetDateTime是一个更好的选择。字符串格式符合 ISO 8601。java.time 类可以直接解析最常见的 ISO 8601 格式变体,无需任何显式格式化程序,因此我们在这里不需要格式化程序。顺便说一句,您分配给格式化程序的区域没有任何区别,因为使用了字符串中的偏移量。
添加回答
举报