我正在尝试使用我在堆栈溢出上找到的示例来解析芬兰语日期,但我不断收到解析异常。
这是我的片段:
SimpleDateFormat dftFormat = new SimpleDateFormat("dd MMMM yyyy", new Locale("fi", "FI"));
Date datDate = dftFormat.parse("25 syyskuu 2012");
DateFormat
字符似乎与英语字符相同,所以我想知道为什么这不起作用。
以下是有关芬兰语区域设置的信息。
谢谢。
似乎所有芬兰日期都以 ta 结尾,即syyskuu
变得syyskuuta
.
我给出的区域设置引用是错误的。如果您看到该链接,您会注意到缺少ta
,这是一些误导性信息。我在 Javadocs 中找不到芬兰语语言环境的确切区域设置信息。
我吸取了教训,多亏了@Eis和@Fildor,使用您的解析格式打印出日期以查看结果字符串是什么。然后,您可以使用格式比较输入字符串是否可解析。
以下是我测试代码的方式:
Date datDate = dftFormat.parse("25 syyskuuta 2012");
System.out.println(new SimpleDateFormat("dd MMMM yyyy").format(datDate));
tl;博士
syyskuu
和syyskuuta
都是芬兰语中September
的正确拼写。第一个用于独立使用,第二个用于上下文。
java.time.Month
枚举可以提供任一形式的拼写。
java.time
我使用现代的java.time类而不是旧的过时的java.util.Date
和java.text.SimpleDateFormat
类尝试了相同的代码。
Java8 及更高版本中内置的 java.time 框架。请参阅甲骨文教程。Java.time的大部分功能在ThreeTen-Backport中向后移植到Java 6和7,并在ThreeTenABP中进一步适应Android。
带格式的日期值字符串
在本例中,我们根据问题实例化 2012 年 9 月 25 日的LocalDate
。
LocalDate ld = LocalDate.of ( 2012 , Month.SEPTEMBER , 25 ); // 2012-09-25
我们得到了一个DateTimeFormatter
,可以在生成字符串时自动本地化。调用ofLocalizedDate
意味着我们的字符串将仅表示日期时间值的日期部分。FormatStyle
控制字符串的长度(完整、长、中、短)。
DateTimeFormatter formatter = DateTimeFormatter.ofLocalizedDate ( FormatStyle.LONG );
接下来,我们将 JVM 当前默认Locale
的分配替换为芬兰和芬兰语言环境。这个Locale
对象决定了两件事:(a)用于翻译诸如日期名称或月份名称之类的片段的人类语言,以及(b)缩写的文化规范,对月份或日期等元素进行排序,逗号与句点的使用等。
Locale locale = new Locale ( "fi" , "FI" );
formatter = formatter.withLocale ( locale );
使用该格式化程序实际生成一个String
来表示我们的LocalDate
值。
String output = ld.format ( formatter ); // 25. syyskuuta 2012
转储到控制台。
System.out.println ( "ld: " + ld + " with locale: " + locale + " | output: " + output );
- >Syyskuuta 2012
如接受的答案所示,java.time 同意syyskuuta
是九月的月份名称。
用于显示的月份名称
java.time 类包括Month
枚举。这个方便的类具有生成字符串的功能,该字符串的月份名称本地化为Locale
。
这种本地化类似于我们在上面的代码中看到的本地化。但不同的是使用不同的枚举来控制文本的长度。在这里,TextStyle
枚举(而不是FormatStyle
)提供完整,狭窄和简短...但也是这三个长度的"独立"版本。在某些语言中,单独使用文本时使用的单词与完整日期使用时使用的单词有所不同。只是为了好玩,让我们用芬兰语试试吧。
Locale locale = new Locale ( "fi" , "FI" );
EnumSet<TextStyle> styles = EnumSet.allOf ( TextStyle.class );
for ( TextStyle style : styles ) {
System.out.println ( style + " | " + Month.SEPTEMBER.getDisplayName ( style , locale ) );
}
谜团解开:独立月份名称
果然,下面的输出解释了这个谜团。芬兰语:
- 单独使用月份名称时,请删除
syyskuu
的ta
。 - 在特定日期时间值的上下文中使用时,包括
syyskuuta
的ta
。
完整 | Syyskuuta
FULL_STANDALONE | Syyskuu
SHORT | syyskuuta
SHORT_STANDALONE | syys
窄 |S
NARROW_STANDALONE |S
如果无法控制应用格式不正确的输入,则可以搜索任何独立值并将其替换为其正确的版本。或者,也许您可以使用DateTimeFormatterBuilder
来期待独立版本(我不知道这是否可能,只是一个想法)。