java.text.ParseException:无法解析的日期“yyyy-MM-dd'T'HH:mm:ss.SSSXXX” - SimpleDateFormat

时间:2018-02-22 08:52:36

标签: java date simpledateformat datetime-parsing

我使用以下代码来解析datetime

String parseDate(String tranDateTime, String originalDateFormat, String toDateFormat) throws ParseException {
    SimpleDateFormat originalMonthYear = new SimpleDateFormat(originalDateFormat);
    Date date = originalMonthYear.parse(tranDateTime);

    SimpleDateFormat formatter = new SimpleDateFormat(toDateFormat);
    return formatter.format(date);
}

并尝试解析日期时间值,如下所示:

parseDate("2017-08-16T00:00:00Z", 
          "yyyy-MM-dd'T'HH:mm:ss.SSSXXX", "yyyy-MM-dd HH:mm:ss");

抛出异常:

  

java.text.ParseException:Unparseable date:“2017-08-16T00:00:00Z”

但是,当我将日期值更改为"2017-08-16T02:54:15.537Z"时,该功能正常。我不知道为什么。

4 个答案:

答案 0 :(得分:5)

问题来自:

Date date = originalMonthYear.parse(tranDateTime);

这个日期

2017-08-16T00:00:00Z

与模式不匹配

yyyy-MM-dd'T'HH:mm:ss.SSSXXX

因为缺少毫秒(SSS部分)

所以

Date date = originalMonthYear.parse(tranDateTime);

引发异常

java.text.ParseException: Unparseable date: "2017-08-16T00:00:00Z"

<强>解决方案

  • 将您的日期2017-08-16T00:00:00Z更改为2017-08-16T00:00:00.000Z(为您的日期添加毫秒数)
  • 将您的模式yyyy-MM-dd'T'HH:mm:ss.SSSXXX更改为yyyy-MM-dd'T'HH:mm:ssXXX(从模式中移除毫秒数)

答案 1 :(得分:3)

您在评论中提到:

  

此外,日期时间值可以是&#34; 2017-08-16T00:00:00Z&#34;要么   &#34; 2017-08-16T00:00:15.537Z&#34;从数据库中检索。我们有吗?   解析这两种格式的一般模式?

更好的是,它们都可以在没有显式模式的情况下解析

    System.out.println(OffsetDateTime.parse("2017-08-16T00:00:00Z"));
    System.out.println(OffsetDateTime.parse("2017-08-16T00:00:15.537Z"));

打印:

2017-08-16T00:00Z
2017-08-16T00:00:15.537Z

格式化,例如:

    DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
    System.out.println(OffsetDateTime.parse("2017-08-16T00:00:00Z").format(formatter));

打印

2017-08-16 00:00:00

我正在使用并热烈推荐现代Java日期和时间API java.timeSimpleDateFormatDate已经过时了,前者尤其出了名的麻烦。现代API可以更好地使用。

您的字符串(尽管存在差异)均符合ISO 8601(日期和时间格式标准)。 java.time类在没有任何显式格式化器的情况下解析这些格式。

链接: Oracle tutorial: Date Time解释如何使用java.time

答案 2 :(得分:1)

2017-08-16T00:00:00Z更改为2017-08-16T00:00:00.000Z,它适用于我。

答案 3 :(得分:1)

问题来源:

问题来自于尝试使用日期格式2017-08-16T00:00:00Z解析日期值yyyy-MM-dd'T'HH:mm:ss.SSSXXX,在行中:

Date date = originalMonthYear.parse(tranDateTime);

查看值和格式之间的区别:

 ______________________________
|2017|08|16| T |00|00|00Z      |
|yyyy|MM|dd|'T'|HH|mm|ss.SSSXXX|
|____|__|__|___|__|__|_________|

解决方案

简单的一个是:

Date date = originalMonthYear.parse("2017-08-16T00:00:00.000Z")

但是,如果您将获得许多不同格式,您可以使用类似(从未测试)的内容:

List<SimpleDateFormat> myUsedPatterns = new ArrayList<>();

myUsedPatterns.add(new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssXXX"));
myUsedPatterns.add(new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSXXX"));

for (SimpleDateFormat myPattern : myUsedPatterns) {
    try {
        SimpleDateFormat originalMonthYear = new SimpleDateFormat(myPattern );
        Date date = originalMonthYear.parse(tranDateTime);

        SimpleDateFormat formatter = new SimpleDateFormat(toDateFormat);
        return formatter.format(date);

    } catch (ParseException e) {
        // Loop
    }
}