首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >用闰秒解析LocalTime

用闰秒解析LocalTime
EN

Stack Overflow用户
提问于 2017-12-28 15:12:22
回答 4查看 824关注 0票数 4

我试图了解如何为我的应用程序构建自定义DateTimeFormatter。我基本上需要处理像这个"HHMMSS.FFFFFF".这样写的时间

我得到了99%的信息:

代码语言:javascript
复制
import static java.time.temporal.ChronoField.HOUR_OF_DAY;
import static java.time.temporal.ChronoField.MICRO_OF_SECOND;
import static java.time.temporal.ChronoField.MINUTE_OF_HOUR;
import static java.time.temporal.ChronoField.SECOND_OF_MINUTE;
public static final DateTimeFormatter MY_TIME;
static {
    MY_TIME = new DateTimeFormatterBuilder()
            .appendValue(HOUR_OF_DAY, 2)
            .appendValue(MINUTE_OF_HOUR, 2)
            .optionalStart()
            .appendValue(SECOND_OF_MINUTE, 2)
            .optionalStart()
            .appendFraction(MICRO_OF_SECOND, 0, 6, true)
            .toFormatter().withResolverStyle(ResolverStyle.STRICT);
}

我可以很好地处理输入:

代码语言:javascript
复制
String text = "101530";
LocalTime lt = LocalTime.parse(text, MY_TIME);

甚至是

代码语言:javascript
复制
String text = "070907.0705";
LocalTime lt = LocalTime.parse(text, MY_TIME);

代码语言:javascript
复制
String text = "0000";
LocalTime lt = LocalTime.parse(text, MY_TIME);

但是,由于某些原因,我无法理解处理闰秒的API,因此对于我来说,下面的操作总是失败的:

代码语言:javascript
复制
String text = "235960";
LocalTime lt = LocalTime.parse(text, MY_TIME);

我应该如何构建我的DateTimeFormatterBuilder以便处理闰秒呢?

更新:我非常喜欢ResolverStyle.STRICT,因为它拒绝无效的输入,例如:

  • "251213“或者
  • "126100“

所以我不能在这种情况下使用ResolverStyle.LENIENT,我只想要闰秒的额外特例。

EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2017-12-28 16:05:19

由于这对我的用户是有限的(编辑无效的时间),所以我可以使用以下简单的方法来处理这个特殊情况:

代码语言:javascript
复制
if (text.length() >= 6 && "60".equals(text.substring(4, 6))) {
    String newText = text.substring(0, 4) + "59" + text.substring(6);
    return LocalTime.parse(newText, MY_TIME);
}
return LocalTime.parse(text, MY_TIME);

这似乎是一种普遍接受的黑客行为:

票数 0
EN

Stack Overflow用户

发布于 2017-12-28 17:32:19

不显示日历日期和时区,显示闰秒的本地时钟时间就没有多大意义。否则,您就不知道要解析的字符串是否真的有效( java.time-package将不会帮助您验证它),或者只是以一种宽容的方式(即将"60“解析为下一秒)。

关于java.time的闰秒功能

java.time确实可以容忍任何虚拟约会,并结合一个闰秒,尽管这在大多数情况下是错误的。DateTimeFormatter只接受UTC-偏移零,但不接受像"2012-07-01T08:59:60+0900“这样的表达式。

此外:java.time.Instant无法存储闰秒信息,而是将其丢弃。对于可能的闰秒标志,只能使用查询解析器。然后,这取决于你如何处理这些信息。

结论:如果你想忽略闰秒信息,但在输入时容忍它,这种方法对你来说是很好的。

替代办法:

如果您真的对解析、验证和评估可能的闰秒感兴趣,那么我建议您使用我的库Time4J。但它确实需要一个有效的日历日期(只在很少的日期插入闰秒)。

代码语言:javascript
复制
     ChronoFormatter<Moment> formatter = 
         ChronoFormatter.ofMomentPattern( 
             "uuuu-MM-dd'T'HH:mm:ss XXX", 
             PatternType.CLDR, 
             Locale.ROOT, 
             ZonalOffset.UTC 
         )
     Moment m = formatter.parse("2012-07-01T08:59:60+09:00");

     // this conversion throws away the leap second
     Instant i = m.toTemporalAccessor();

有关更多信息,请参见我关于DZone的文章。

票数 3
EN

Stack Overflow用户

发布于 2017-12-28 15:36:12

来自java.time.Instant JavaDoc的相关描述:

..。这个Java定义了它自己的时间尺度,即Java时间尺度. ..。 使用JSR-310 API实现Java时间刻度不需要提供任何亚秒精确的时钟,也不需要提供单调或平滑的时钟。因此,实现并不需要来实际执行UTC或,否则就需要注意闰秒。 ..。 Java时间尺度用于所有日期时间类.这包括即时,LocalDate,LocalTime,OffsetDateTime,ZonedDateTime和持续时间。

简而言之,您不应该期望java.time API注意到闰秒。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/48009870

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档