使用ThreeTen-Extra解析YearQuarter时,可以拒绝多个四分之一位数吗?

问题描述 投票:3回答:2

我使用YearQuarter库中的ThreeTen-Extra代表给定年份内的特定季度。

我使用的是自定义格式而不是默认格式,例如2018年第三季度的“3Q2018”而不是“2018-Q3”。当通过YearQuarter.parse(text, formatter)解析一个值时,我希望拒绝该季度前导零的值(通过标准的DateTimeParseException)。

我的第一次尝试是使用DateTimeFormatter.ofPattern("Q'Q'yy")。但是,这会在本季度前接受任意多个前导零的字符串。例如,此格式化程序不会拒绝“02Q2007”或“002Q2007”。

这似乎与如何处理其他时间类型的单个字符模式一致。例如,这些成功解析没有错误:

YearMonth.parse("012-2018", DateTimeFormatter.ofPattern("M-yyyy"))
LocalTime.parse("001:00:01", DateTimeFormatter.ofPattern("H:mm:ss"))
LocalTime.parse("01:00:012", DateTimeFormatter.ofPattern("HH:mm:s"))

但是,这些用DateTimeParseException拒绝输入:

YearMonth.parse("012-2018", DateTimeFormatter.ofPattern("MM-yyyy"))
LocalTime.parse("001:00:01", DateTimeFormatter.ofPattern("HH:mm:ss"))
LocalTime.parse("01:00:012", DateTimeFormatter.ofPattern("HH:mm:ss"))

我如何构建一个DateTimeFormatter来解析我所需格式的YearQuarter,同时拒绝该季度超过一位数的值?理想情况下,我希望将其作为模式字符串,因为人们更容易阅读,并且更容易外化为文本属性。

java java-time
2个回答
0
投票

我还没有发现一种方法来做一个模式字符串,但以下将以编程方式构造一个具有所需格式的DateTimeFormatter,拒绝0填充的四分之一:

import java.time.format.DateTimeFormatterBuilder;
import java.time.temporal.ChronoField;
import java.time.temporal.IsoFields;

[...]

new DateTimeFormatterBuilder()
    .appendValue(IsoFields.QUARTER_OF_YEAR, 1)
    .appendLiteral('Q')
    .appendValue(ChronoField.YEAR, 4)
    .toFormatter();

0
投票

如果你坚持使用模式字符串,那么我担心在DateTimeFormatter的上下文中没有办法,但我已成功测试了我的lib Time4J,如果它提供了所需的行为:

    ChronoFormatter<CalendarQuarter> f =
        ChronoFormatter.ofPattern(
            "Q'Q'uuuu", PatternType.CLDR, Locale.ROOT, CalendarQuarter.chronology());
    CalendarQuarter cq = f.parse("3Q2018");
    System.out.println(cq); // 2018-Q3
    f.parse("13Q2018"); // exception
    f.parse("03Q2018"); // exception

CalendarQuarter类型的对象对应于YearQuarter,因此您可以找到类似的方法将其更改为格里高利日期,例如:

    CalendarQuarter cq = f.parse("3Q2018");
    LocalDate ld = cq.atEndOfQuarter().toTemporalAccessor();
    System.out.println(ld); // 2018-09-30
© www.soinside.com 2019 - 2024. All rights reserved.