JDK dateformater在德语语言环境中解析DayOfWeek,java8 vs java9

use*_*547 16 java java-8 java-time java-9

我在Java 8(1.8.0_77)和Java 9(Java HotSpot(TM)64位服务器VM(构建9 + 181,混合模式)中尝试了一些代码)

DateTimeFormatter dtf = DateTimeFormatter.ofPattern("eee", Locale.GERMAN);
DayOfWeek mo = dtf.parse("Mo", DayOfWeek::from);
System.out.println("mo = " + mo);
Run Code Online (Sandbox Code Playgroud)

我不太熟悉这些类的细节,但在Java 8中这个工作,打印:

mo =星期一

在Java 9中,它失败了

线程"main"中的异常java.time.format.DateTimeParseException:无法在java.base上的java.base/java.time.format.DateTimeFormatter.parseResolved0(DateTimeFormatter.java:1988)的索引0处解析文本"Mo"在day.main(day.java:10)的/java.time.format.DateTimeFormatter.parse(DateTimeFormatter.java:1890)

任何想法,这是可重现的吗?

因此,在格式化时:使用此代码:

DateTimeFormatter dtf = DateTimeFormatter.ofPattern("eee", Locale.GERMAN);
String format = dtf.format(DayOfWeek.MONDAY);
System.out.println("format = " + format);
Run Code Online (Sandbox Code Playgroud)

jdk1.8.0-77:

格式= Mo.

jdk-9(build 9 + 181)

格式= Mo.

Nam*_*man 12

由于CLDR日期时间模式的当前实现以及JEP-252的实现,这似乎存在于,其中指出了

默认情况下,使用Unicode Consortium的公共区域设置数据存储库(CLDR)中的区域设置数据.

用于格式化和翻译显示字符串的本地化模式(例如区域设置名称)在某些区域设置中可能不同.

要启用与JDK 8兼容的行为,请将系统属性设置为CLDR之前的COMPATjava.locale.providers值.


而在其数据部分的第二部分,德国语言环境中具有以下相关信息的Unicode国际组件可以证明该行为是有意的 -

在此输入图像描述

编辑/注意:由@ManiGrover链接,迁移指南对此类实现发出了类似的警告 -

如果您的应用程序成功启动,请仔细查看您的测试并确保其行为与JDK 8上的行为相同.例如,一些早期采用者已注意到他们的日期和货币的格式不同.请参阅默认使用CLDR区域设置数据.

  • 来自https://docs.oracle.com/javase/9​​/migrate/toc.htm#JSMIG-GUID-AFD3BDEC-99FC-4F3C-946F-A1CD2D05B74B"如果您的应用程序成功启动,请仔细查看您的测试并确保行为与JDK 8上的行为相同.例如,一些早期采用者注意到他们的日期和货币的格式不同.请参阅默认情况下使用CLDR区域设置数据. (3认同)

Men*_*ild 8

没有点的abbreviatiions"Mo","Di"等在CLDR中没有消失,但可以通过独立模式访问.您应该使用独立格式符号"c"而不是"e"更改模式:

DateTimeFormatter dtf = DateTimeFormatter.ofPattern("ccc", Locale.GERMAN);
DayOfWeek mo = dtf.parse("Mo", DayOfWeek::from);
Run Code Online (Sandbox Code Playgroud)

实际上,我认为基础数据的变化是破坏向后兼容性(具体如行为中断).

  • 默认情况下,过渡到使用CDLR语言环境数据确实是一种破坏性的变化.JDK 8包含CDLR语言环境数据,因此您可以使用`-Djava.locale.providers = CLDR`运行,以便在转移到JDK 9之前识别任何问题. (6认同)