简体   繁体   English

将字符串解析为LocalDateTime时出现DateTimeParseException

[英]DateTimeParseException when parsing String to LocalDateTime

The following works perfectly: 以下内容非常适用:

String startDate = "2019-10-12T00:00:00.000-07:00"

LocalDateTime startDateTime = LocalDateTime.parse(startDate,
    DateTimeFormatter.ISO_ZONED_DATE_TIME);

However, for the following code: 但是,对于以下代码:

String startDate = "2019-10-12T00:00:00.000+07:00"

LocalDateTime startDateTime = LocalDateTime.parse(startDate,
    DateTimeFormatter.ISO_ZONED_DATE_TIME);

I get an exception: 我有一个例外:

throws java.time.format.DateTimeParseException : Text '2019-10-12T00:00:00.000 07:00' could not be parsed at index 23 引发java.time.format.DateTimeParseException :无法在索引23处解析文本'2019-10-12T00:00:00.000 07:00'

Can someone help me understand what might be possibly wrong here? 有人可以帮助我了解这里可能出什么问题吗?

I tried running both dates locally with the same parsing of the LocalDateTime , and they both run correctly . 我尝试使用LocalDateTime的相同解析在本地运行两个日期,并且它们都正确运行

I could recreate your same error by using a different date (note the space at the zone offset, instead of a + or - ) 2019-10-12T00:00:00.000 07:00 instead of 2019-10-12T00:00:00.000+07:00 . 我可以通过使用不同的日期(请注意区域偏移量处的空格 ,而不是+- )来重新创建相同的错误2019-10-12T00:00:00.000 07:00而不是2019-10-12T00:00:00.000+07:00 Which is what your error message shows (but not what your code has). 错误消息显示的是什么(但代码没有显示)。

Are you sure that the code version you show, which uses 2019-10-12T00:00:00.000+07:00 , is the actual version that produces the error? 您确定显示的使用2019-10-12T00:00:00.000+07:00的代码版本是产生错误的实际版本吗? It looks like you have been using 2019-10-12T00:00:00.000 07:00 , which then leads to the error. 看来您一直在使用2019-10-12T00:00:00.000 07:00 ,然后导致错误。

tl;dr tl; dr

(A) As mentioned in comment by Andreas , the disappearance of your + character in error message is suspicious. (A)如Andreas的评论中所述,错误消息中+字符的消失是可疑的。 You likely have a character encoding problem. 您可能有字符编码问题。 We here do not have enough info to diagnose that. 我们这里没有足够的信息来诊断。

(B) Use OffsetDateTime rather than LocalDateTime , to fit your data. (B)使用OffsetDateTime而不是LocalDateTime来适合您的数据。

OffsetDateTime
.parse( "2019-10-12T00:00:00.000+07:00" )
.toInstant()
.toString()

2019-10-11T17:00:00Z 2019-10-11T17:00:00Z

See this code run live at IdeOne.com . 看到此代码在IdeOne.com上实时运行

LocalDateTime is the wrong class LocalDateTime是错误的类

The LocalDateTime class lacks any concept of time zone or offset-from-UTC. LocalDateTime类缺少任何时区或从UTC偏移的概念。 So it cannot, by definition, represent a moment. 因此,根据定义,它不能代表一个时刻。 A LocalDateTime object is not a point on the timeline. LocalDateTime对象不是时间轴上的点。

Yet your input string indicates an offset-from-UTC, the +07:00 in 2019-10-12T00:00:00.000+07:00 . 然而,你输入的字符串表示偏移从-UTC的+07:002019-10-12T00:00:00.000+07:00 Your attempt to put this value in a LocalDateTime is a misfit, a square peg in a round hole . 您尝试将此值放入LocalDateTime是不合适的,是圆孔中方钉

Never use LocalDateTime when you mean a specific moment, a specific point on the timeline. 当您表示时间轴上的特定时刻,特定点时,切勿使用LocalDateTime This class is almost never used in business-oriented apps for present or past moments. 目前或过去,此类类几乎从未在面向业务的应用程序中使用。 When making appointments in the future, this class should be used when you want the time-of-day to remain the same regardless of politicians redefining the region's time zone. 将来进行约会时,无论政客是否重新定义该地区的时区,只要您希望时间保持不变,都应使用此类。

OffsetDateTime

Parse as an OffsetDateTime object. 解析为OffsetDateTime对象。

Your input string happens to comply fully with the ISO 8601 standard for textual date-time formats. 您的输入字符串恰好完全符合用于文本日期时间格式的ISO 8601标准。 The java.time classes use these formats by default when parsing/generating strings. 解析/生成字符串时, java.time类默认使用这些格式。 So no need to specify a formatting pattern. 因此,无需指定格式化模式。

String input = "2019-10-12T00:00:00.000+07:00" ;
OffsetDateTime odt = OffsetDateTime.parse( input ) ;

UTC 世界标准时间

To adjust to the wall-clock time of UTC (an offset of zero), call OffsetDateTime::withOffsetSameInstant . 要适应UTC的挂钟时间(偏移量为零),请调用OffsetDateTime::withOffsetSameInstant For your convenience, use the constant ZoneOffset.UTC . 为了方便起见,请使用常量ZoneOffset.UTC

OffsetDateTime odtUtc = odt.withOffsetSameInstant( ZoneOffset.UTC ) ;

Or simply extract an object of the basic building-block class in java.time , an Instant . 或者简单地在java.time中提取基本构建基类的对象 ,即Instant An Instant is always in UTC, by definition. 根据定义, Instant始终使用UTC。

Instant instant = odt.toInstant() ;

ZonedDateTime

To see the same moment as viewed through the wall-clock time used by the people of a particular region (a time zone), apply a ZoneId to get a ZonedDateTime . 要查看特定区域(时区)的人们在墙上时钟所看到的相同时刻,请应用ZoneId以获得ZonedDateTime

ZoneId z = ZoneId.of( "Africa/Tunis" ) ;
ZonedDateTime zdt = odt.atZoneSameInstant( z ) ;

About java.time 关于java.time

The java.time framework is built into Java 8 and later. java.time框架内置于Java 8及更高版本中。 These classes supplant the troublesome old legacy date-time classes such as java.util.Date , Calendar , & SimpleDateFormat . 这些类取代了麻烦的旧的旧式日期时间类,例如java.util.DateCalendarSimpleDateFormat

The Joda-Time project, now in maintenance mode , advises migration to the java.time classes. 现在处于维护模式Joda-Time项目建议迁移到java.time类。

To learn more, see the Oracle Tutorial . 要了解更多信息,请参见Oracle教程 And search Stack Overflow for many examples and explanations. 并在Stack Overflow中搜索许多示例和说明。 Specification is JSR 310 . 规格为JSR 310

You may exchange java.time objects directly with your database. 您可以直接与数据库交换java.time对象。 Use a JDBC driver compliant with JDBC 4.2 or later. 使用与JDBC 4.2或更高版本兼容的JDBC驱动程序 No need for strings, no need for java.sql.* classes. 不需要字符串,不需要java.sql.*类。

Where to obtain the java.time classes? 在哪里获取java.time类?

The ThreeTen-Extra project extends java.time with additional classes. ThreeTen-Extra项目使用其他类扩展了java.time。 This project is a proving ground for possible future additions to java.time. 该项目为将来可能在java.time中添加内容提供了一个试验场。 You may find some useful classes here such as Interval , YearWeek , YearQuarter , and more . 您可以在这里找到一些有用的类,比如IntervalYearWeekYearQuarter ,和更多

在startDateTime中有一个额外的零,请使用startDateTime =“ 2019-10-12T00:00:00.00 + 07:00”

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

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM