解析日期的优雅解决方案
Elegant solution to parse date
我想将一些文本解析为日期。但是,不能保证文本具有所需的格式。它可能是 2012-12-12
或 2012
甚至 </code>.</p>
<p>目前,我正在使用嵌套的 try-catch 块,但这不是一个好的方向(我想)。</p>
<pre><code>LocalDate parse;
try {
parse = LocalDate.parse(record, DateTimeFormatter.ofPattern("uuuu/MM/dd"));
} catch (DateTimeParseException e) {
try {
Year year = Year.parse(record);
parse = LocalDate.from(year.atDay(1));
} catch (DateTimeParseException e2) {
try {
// and so on
} catch (DateTimeParseException e3) {}
}
}
这个问题的优雅解决方案是什么?如果在评估期间发生异常,是否可以使用不存在的 Optional
s ?如果是,如何?
这可以使用 DateTimeFormatter
可选部分以优雅的方式完成。可选部分以 [
标记开始,以 ]
标记结束。
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("[yyyy[-MM-dd]]");
System.out.println(formatter.parse("2012-12-12")); // prints "{},ISO resolved to 2012-12-12"
System.out.println(formatter.parse("2012")); // prints "{Year=2012},ISO"
System.out.println(formatter.parse("")); // prints "{},ISO"
DateTimeFormatterBuilder
class 包含实现此功能的构建块:
LocalDate now = LocalDate.now();
DateTimeFormatter fmt = new DateTimeFormatterBuilder()
.appendPattern("[uuuu[-MM[-dd]]]")
.parseDefaulting(ChronoField.YEAR, now.getYear())
.parseDefaulting(ChronoField.MONTH_OF_YEAR, now.getMonthValue())
.parseDefaulting(ChronoField.DAY_OF_MONTH, now.getDayOfMonth())
.toFormatter();
System.out.println(LocalDate.parse("2015-06-30", fmt));
System.out.println(LocalDate.parse("2015-06", fmt));
System.out.println(LocalDate.parse("2015", fmt));
System.out.println(LocalDate.parse("", fmt));
parseDefaulting()
方法允许为特定字段设置默认值。在所有情况下,都可以从结果中解析出 LocalDate
,因为有足够的信息可用。
另请注意模式中使用“[...]”部分来定义可选内容。
我想将一些文本解析为日期。但是,不能保证文本具有所需的格式。它可能是 2012-12-12
或 2012
甚至 </code>.</p>
<p>目前,我正在使用嵌套的 try-catch 块,但这不是一个好的方向(我想)。</p>
<pre><code>LocalDate parse;
try {
parse = LocalDate.parse(record, DateTimeFormatter.ofPattern("uuuu/MM/dd"));
} catch (DateTimeParseException e) {
try {
Year year = Year.parse(record);
parse = LocalDate.from(year.atDay(1));
} catch (DateTimeParseException e2) {
try {
// and so on
} catch (DateTimeParseException e3) {}
}
}
这个问题的优雅解决方案是什么?如果在评估期间发生异常,是否可以使用不存在的 Optional
s ?如果是,如何?
这可以使用 DateTimeFormatter
可选部分以优雅的方式完成。可选部分以 [
标记开始,以 ]
标记结束。
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("[yyyy[-MM-dd]]");
System.out.println(formatter.parse("2012-12-12")); // prints "{},ISO resolved to 2012-12-12"
System.out.println(formatter.parse("2012")); // prints "{Year=2012},ISO"
System.out.println(formatter.parse("")); // prints "{},ISO"
DateTimeFormatterBuilder
class 包含实现此功能的构建块:
LocalDate now = LocalDate.now();
DateTimeFormatter fmt = new DateTimeFormatterBuilder()
.appendPattern("[uuuu[-MM[-dd]]]")
.parseDefaulting(ChronoField.YEAR, now.getYear())
.parseDefaulting(ChronoField.MONTH_OF_YEAR, now.getMonthValue())
.parseDefaulting(ChronoField.DAY_OF_MONTH, now.getDayOfMonth())
.toFormatter();
System.out.println(LocalDate.parse("2015-06-30", fmt));
System.out.println(LocalDate.parse("2015-06", fmt));
System.out.println(LocalDate.parse("2015", fmt));
System.out.println(LocalDate.parse("", fmt));
parseDefaulting()
方法允许为特定字段设置默认值。在所有情况下,都可以从结果中解析出 LocalDate
,因为有足够的信息可用。
另请注意模式中使用“[...]”部分来定义可选内容。