Java 8 ZoneDateTime
我正在尝试使用ZoneDateTime.nowZoneOffset.UTC.toString获取当前时间。它工作得很好,但是当它们正好处于滚动00.000Z时,似乎会切断秒/毫秒,或者看起来是这样。通常情况下,这并不重要,但我正在将数据写入ElasticSearch,它对我经过的日期有严格的映射 我可能对正在发生的事情不感兴趣,但我想尝试确保我总能提供一个以秒和毫秒为单位的日期/时间 基本代码段的第一步是添加毫秒,但秒也可能被忽略:Java 8 ZoneDateTime,java,groovy,Java,Groovy,我正在尝试使用ZoneDateTime.nowZoneOffset.UTC.toString获取当前时间。它工作得很好,但是当它们正好处于滚动00.000Z时,似乎会切断秒/毫秒,或者看起来是这样。通常情况下,这并不重要,但我正在将数据写入ElasticSearch,它对我经过的日期有严格的映射 我可能对正在发生的事情不感兴趣,但我想尝试确保我总能提供一个以秒和毫秒为单位的日期/时间 基本代码段的第一步是添加毫秒,但秒也可能被忽略: def utcDate = ZonedDateTime.now
def utcDate = ZonedDateTime.now(ZoneOffset.UTC)
def utcDateStr = utcDate.toString()
utcDateStr = utcDateStr.contains(".") ? utcDateStr
: utcDateStr.replace("Z","").concat(".000Z")
希望它采用以下格式,几乎总是这样:
2016-06-16T05:43:07.624Z
首先,听起来你真的想要一个瞬间,而不是一个分区的DateTime——这就完全消除了时区部分。但无论哪种方式,只需使用一个按需设置值的格式即可 听起来你想在Java中找到类似的东西;适当调整到Groovy:
DateTimeFormatter formatter = DateTimeFormatter
.ofPattern("uuuu-MM-dd'T'HH:mm:ss.SSS'Z'", Locale.US)
.withZone(ZoneOffset.UTC);
Instant now = Instant.now();
String text = formatter.format(now);
System.out.println(text);
即使毫秒值为0,它仍将输出毫秒值
如果确实要使用ZoneDateTime,可以使用相同的格式化程序。但从概念上讲,我认为你试图表达的只是时间上的一个瞬间,而瞬间更适合于此。首先,听起来你真的想要一个瞬间,而不是一个分区的DateTime——这就完全消除了时区部分。但无论哪种方式,只需使用一个按需设置值的格式即可 听起来你想在Java中找到类似的东西;适当调整到Groovy:
DateTimeFormatter formatter = DateTimeFormatter
.ofPattern("uuuu-MM-dd'T'HH:mm:ss.SSS'Z'", Locale.US)
.withZone(ZoneOffset.UTC);
Instant now = Instant.now();
String text = formatter.format(now);
System.out.println(text);
即使毫秒值为0,它仍将输出毫秒值
如果确实要使用ZoneDateTime,可以使用相同的格式化程序。但从概念上讲,我认为您试图表示的只是时间上的一个瞬间,而瞬间更适合于此。如果您想使用格式化程序,您可以这样构建一个:
DateTimeFormatter ES_ISO8601_FORMATTER = new DateTimeFormatterBuilder()
.parseCaseInsensitive()
.append(
new DateTimeFormatterBuilder()
.parseCaseInsensitive()
.append(ISO_LOCAL_DATE)
.appendLiteral('T')
.append(
new DateTimeFormatterBuilder()
.appendValue(HOUR_OF_DAY, 2)
.appendLiteral(':')
.appendValue(MINUTE_OF_HOUR, 2)
.appendLiteral(':')
.appendValue(SECOND_OF_MINUTE, 2)
.appendFraction(NANO_OF_SECOND, 3, 9, true)
.toFormatter()
)
.toFormatter()
)
.appendOffsetId()
.toFormatter();
这是从Java8中DateTimeFormatter类中的代码拼凑而成的
这一变化基本上是给人的
.appendFraction(NANO_OF_SECOND, 3, 9, true)
最小宽度为3,而不是原始ISO格式化程序中的0。如果您想使用格式化程序路径,可以这样构建一个:
DateTimeFormatter ES_ISO8601_FORMATTER = new DateTimeFormatterBuilder()
.parseCaseInsensitive()
.append(
new DateTimeFormatterBuilder()
.parseCaseInsensitive()
.append(ISO_LOCAL_DATE)
.appendLiteral('T')
.append(
new DateTimeFormatterBuilder()
.appendValue(HOUR_OF_DAY, 2)
.appendLiteral(':')
.appendValue(MINUTE_OF_HOUR, 2)
.appendLiteral(':')
.appendValue(SECOND_OF_MINUTE, 2)
.appendFraction(NANO_OF_SECOND, 3, 9, true)
.toFormatter()
)
.toFormatter()
)
.appendOffsetId()
.toFormatter();
这是从Java8中DateTimeFormatter类中的代码拼凑而成的
这一变化基本上是给人的
.appendFraction(NANO_OF_SECOND, 3, 9, true)
最小宽度为3,而不是原始ISO格式化程序中的0如果您说调用toString会减少秒/毫秒,则会更清楚。。。否则,它听起来就像现在自己被打破了。啊,好的观点@JonSkeet。你是对的,我会编辑/修复这个问题如果你说调用toString会减少秒/毫秒,那会更清楚。。。否则,它听起来就像现在自己被打破了。啊,好的观点@JonSkeet。如果你是对的,我将编辑/修复这个问题。你选择uuuu而不是更常见的yyyy有什么特殊原因吗?@shmosel:最初,因为yyyy不起作用。uuuu也没有,因为我没有设置时区。。。但无论如何,yyyy是纪年,这意味着1905年实际上在公元1905年和公元前1905年之间是不明确的。不太可能是个问题,但在我看来,仅仅一年就稍微干净了一点。您选择uuuu而不是更常见的yyyy有什么特别的原因吗?@shmosel:最初,因为yyyy不起作用。uuuu也没有,因为我没有设置时区。。。但无论如何,yyyy是纪年,这意味着1905年实际上在公元1905年和公元前1905年之间是不明确的。这不太可能是个问题,但就国际海事组织而言,今年的情况稍微好一点。