简体   繁体   English

删除日期时间字符串中的纳秒

[英]Removing nanoseconds in a datetime string

What I'm trying to achieve... 我想要实现的目标......

I have dates in potentially 2 formats: 我有可能有2种格式的日期:

2013-07-03T14:30:38Z
2013-07-03T14:30:38.000000Z

I want to axe the .00000 if it exists 如果它存在,我想要.00000

I got this far, to remove everything after the '.' 我到目前为止,删除'。'后的所有内容。 time.replaceFirst( "^(.*?)\\\\b\\\\..*$" , "$1"); time.replaceFirst( "^(.*?)\\\\b\\\\..*$" ,“$ 1”);

result: 2013-07-03T14:30:38 结果: 2013-07-03T14:30:38

Problem is, I still need the ' Z ' .. how can I keep the Z ? 问题是,我仍然需要' Z '..我怎么能保持Z

I'm no Date Time expert... 我不是约会时间专家......

so I'm not entirely sure if there will always be 6 0s (if the string contains the nanoseconds) or if there can be a variable number of 0s... 所以我不完全确定是否总会有6 0(如果字符串包含纳秒)或者是否可以有0的可变数量...

Java 8 Java 8

I'm using java but didn't want to tag it as java since it's basically just pure regex 我正在使用java但不想将其标记为java,因为它基本上只是纯正则表达式

Simply add the Z back inside: 只需将Z添加回内部:

time.replaceFirst( "^(.*?)\\b\\..*$", "$1Z");

And alternative would be to capture everything until you encounter the period character ( . ): 另一种方法是捕获所有内容,直到遇到句点字符( . ):

time.replaceFirst( "^([^.]+).*(Z)$", "$1$2");

Strings != Date-Time 字符串!=日期时间

I should correct the terminology in the Question: You (apparently) have strings in a certain format, not "dates". 我应该更正问题中的术语:你(显然)有某种格式的字符串 ,而不是“日期”。 Do not confuse date-time values with their String representations. 不要将日期时间值与其字符串表示混淆。

Just as "$12.34" is not a number, it is a string representation of a number with a certain format applied. 正如“$ 12.34”不是数字一样,它是应用了某种格式的数字的字符串表示。 That string can be parsed into a number. 该字符串可以解析为数字。

This concept is the essence of the following code. 这个概念是以下代码的本质。 We parse a string to instantiate a date-time object, then use that date-time object to generate a new string representation. 我们解析一个字符串来实例化一个日期时间对象,然后使用该日期时间对象生成一个新的字符串表示。

java.time java.time

Java 8 and later has a new java.time framework built-in ( Tutorial ). Java 8及更高版本内置了一个新的java.time框架Tutorial )。 You could use that for parsing a string as a date-time value, and then generating a new string representation in any format you desire. 您可以使用它将字符串解析为日期时间值,然后以您希望的任何格式生成新的字符串表示形式。 Here's some code if you want to explore this as an alternative to regex. 如果你想探索这个作为正则表达式的替代品,这里有一些代码。

Both of your possible formats are nearly in ISO 8601 format. 两种可能的格式都接近ISO 8601格式。 Strictly speaking the standard expects only millisecond resolution (3 decimal places) as far as I know, but the java.time framework extends that to nanosecond (up to 9 decimal places). 严格来说,就我所知,标准只需要毫秒级的分辨率(3位小数),但java.time框架将其扩展到纳秒 (最多9位小数)。

The java.time framework uses ISO 8601 as its default when parsing and generating strings. 解析和生成字符串时,java.time框架使用ISO 8601作为其默认值。 So you need not specify a formatter pattern, and instead can use one of the several predefined formatters aimed at ISO 8601 standard formats. 因此,您无需指定格式化程序模式,而是可以使用针对ISO 8601标准格式的多个预定义格式化程序之一。

An Instant object represents a moment on the timeline in UTC . Instant对象表示UTC时间轴上的时刻。 You could assign a particular time zone to get a ZonedDateTime , but not needed for this particular Question. 您可以指定特定时区来获取ZonedDateTime ,但此特定问题不需要。 This class can parse your input strings by default. 默认情况下,此类可以解析输入字符串。

String input = "2013-07-03T14:30:38.123456789Z";
Instant instant = Instant.parse( input );

After parsing we have an instant object in hand. 解析后,我们手头有一个instant对象。 From there we can effectively truncate the fractions of a second by calling the with method to change the fractional second to zero. 从那里我们可以通过调用with方法将小数秒更改为零来有效地截断一秒的分数。 Technically speaking we are not changing the fractional seconds, as java.time uses immutable objects . 从技术上讲,我们不会改变小数秒,因为java.time使用不可变对象 A new object is created based on the values of the original. 基于原始值创建新对象。

Instant instantTruncated = instant.with( ChronoField.NANO_OF_SECOND , 0 );

Lastly we use the predefined formatter, DateTimeFormatter.ISO_INSTANT . 最后,我们使用预定义的格式化程序DateTimeFormatter.ISO_INSTANT This formatter automatically suppresses the fractional zero from the generated string in groups of three digits where the value is zero. 此格式化程序会自动抑制生成的字符串中的小数零,其中三位数的值为零。 So …7.12 prints as …7.120 , …7.1234 as …7.123400 , and …7.0 as …7 . 所以…7.12打印为…7.120…7.1234…7.123400…7.0…7 That last value is fits our needs. 最后一个值符合我们的需求。

DateTimeFormatter formatter = DateTimeFormatter.ISO_INSTANT;
String output = formatter.format( instantTruncated );

The toString method on Instant uses the formatter DateTimeFormatter.ISO_INSTANT by default. Instant上的toString方法默认使用格式化程序DateTimeFormatter.ISO_INSTANT So technically we could shorten the code to just call toString . 所以从技术上讲,我们可以缩短代码来调用toString But I want to show explicitly how a formatter is involved. 但我想明确地说明格式化程序是如何涉及的。

Dump to console. 转储到控制台。

System.out.println( "instant: " + instant );
System.out.println( "instantTruncated: " + instantTruncated );
System.out.println( "output: " + output );

When run. 跑步时

instant: 2013-07-03T14:30:38.123456789Z
instantTruncated: 2013-07-03T14:30:38Z
output: 2013-07-03T14:30:38Z

We can assign a time zone to that Instant to get a 'ZonedDateTime`. 我们可以为该Instant分配一个时区来获得'ZonedDateTime`。

ZoneId zoneId = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = ZonedDateTime.ofInstant( instantTuncated , zoneId);

I'm using java but didn't want to tag it as java since it's basically just pure regex 我正在使用java但不想将其标记为java,因为它基本上只是纯正则表达式

It's probably best to approach with java.time , 最好接近java.time
but since you insist: 但既然你坚持:

time.replaceFirst( "\\.\\d*(Z)?$", "$1");

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 JAX-WS dateTime(以纳秒为单位) - JAX-WS dateTime with nanoseconds 以纳秒为单位的字符串日期转换 - String-Date conversion with nanoseconds 如何使用时区解析日期时间,但没有 T 或纳秒 - How to parse datetime with timezone, but no T or nanoseconds 用可变的纳秒数解析Java中的时间戳字符串 - Parse timestamp string in Java with variable number of nanoseconds 使用日期条件和SQL datetime2时,JPA会截断纳秒 - JPA truncates nanoseconds when using date criteria & SQL datetime2 Joda String DateTime to DateTime - Joda String DateTime to DateTime 如何从纪元以来的字符串格式化时间“ 2019-01-25 14:34:34.123456789”在Java中获取纳秒? - How to get nanoseconds since epoch for string formatted time “2019-01-25 14:34:34.123456789” in java? 如何合并两个地图<string, localdatetime>并以纳秒为单位计算值之间的差异</string,> - How to merge two Maps <String, LocalDateTime> and calculate difference between values in nanoseconds 从Joda DateTime对象中删除时区 - Removing time zone from Joda DateTime object 在 Java 中将纳秒转换为毫秒和纳秒 &lt; 999999 - Conversion of nanoseconds to milliseconds and nanoseconds < 999999 in Java
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM