我需要一个表示年、月、周、天、小时、分钟、秒的间隔数据类型。前三个(年、月、天)可以用Period
完成,后三个(小时、分钟、秒)可以用Duration
完成,但它们似乎都不能同时完成。理想情况下,我希望避免必须实现自定义TemporalAmount
。
没有这样的类型是有原因的。没有明确定义的时间间隔,如"天"、"月"或"年":
- 一天并不总是24小时(取决于夏令时、时区和闰秒)
- 每个月有不同的天数
- 闰年有366天
即使您实现了自定义TemporalAmount,在某些情况下,您的代码也很有可能不正确。如果你说明你的实际需求,你可能会得到更好的答案。
之所以不存在这样的类,是因为实际上有两个不同的时间概念:(1)一个固定的秒数,在Java世界中称为持续时间;或者(2)一个变量的秒数,称为周期。该时期试图从的长度变化中抽象出来
- 分钟(闰秒,未实现)
- 天(夏令时)
- 月(28、29、30、31天)
- 年(闰年)
这就是为什么Period
只存储天、月、年,而Duration
只存储秒和纳秒。是的,它们共享相同的时间单位DAY
,但Duration
天被认为是24小时,并直接转换为秒。
2016-02-01至2016-03-01期间为1个月。持续时间是696小时,而不是720小时。你可以说一段时间的持续时间可能会改变。
因此,您需要定义您的应用程序。你想要一个持续时间(固定的秒数)还是一个周期(一年中"发生"一次的事情)?
以下是他们如何在夏令时变化后计算不同时刻的例子:
Duration oneDayDuration = Duration.ofDays(1);
Period oneDayPeriod = Period.ofDays(1);
ZonedDateTime beforeChange = Instant.parse("2015-10-25T00:00:00.00Z").atZone(ZoneId.of("Europe/Berlin"));
System.out.println(beforeChange);
System.out.println(oneDayDuration.addTo(beforeChange));
System.out.println(oneDayPeriod.addTo(beforeChange));
将打印
2015-10-25T02:00+02:00[Europe/Berlin]
2015-10-26T01:00+01:00[Europe/Berlin]
2015-10-26T02:00+01:00[Europe/Berlin]