无法解析日期异常

Getting unable to parse date exception

我有字符串类型的日期和时间 20/03/2018, 18:20:44 是否可以将其更改为 java 中的日期格式?我试过这段代码:

public static Date getDate(String dateString) {
    DateFormat formatter = new SimpleDateFormat("dd/mm/yyyy hh:mm:ss");
    formatter.setTimeZone(TimeZone.getTimeZone("PST"));
    try {
        Date date = formatter.parse(dateString);
        return date;
    } catch (ParseException e) {
        logger.error("error while parsing milliseconds to date" + dateString, e);
    }
    return null;
}

我无法解析异常并返回 null

您在简单的日期格式中使用了错误的字符串替换,应该是 dd/MM/yyyy, HH:mm:ss。还要注意 HH 的大写,您的时间是 24 小时制,因此必须 HH 超过 hh

因此,应用更改后,您的代码将如下所示:

public static Date getDate(String dateString) {
  DateFormat formatter = new SimpleDateFormat("dd/MM/yyyy, HH:mm:ss");
  formatter.setTimeZone(TimeZone.getTimeZone("PST"));
  try {
    return formatter.parse(dateString);
  } catch (ParseException e) {
    logger.error("error while parsing milliseconds to date" + dateString, e);
  }
  return null;
}

详细了解日期的各种可用格式 here, as an aside it is generally recommended to use the ISO 8601,因此您的日期格式为 yyyy-MM-ddTHH:mm:ss

您应该使用与输入字符串相同的格式:

DateFormat formatter = new SimpleDateFormat("dd/MM/yyyy, hh:mm:ss");

你犯了两个错误:

  • mm代表分钟。 MM代表月份。
    但是您在日期格式的月份部分指定 mm
  • 输入中提供的逗号 , 也必须出现在日期格式中。

因此,对于这种形式的字符串输入:"20/03/2018, 18:20:44",您应该使用这种 DateFormat:

DateFormat formatter = new SimpleDateFormat("dd/MM/yyyy, hh:mm:ss");

tl;博士

您的格式设置不正确,使用了错误的大小写并省略了逗号。

此外,您使用的麻烦 classes 多年前被 java.time classes.

取代
LocalDateTime.parse(                                       // Create a `LocalDateTime` object as the input string lacks any time zone or offset-from-UTC.
    "20/03/2018, 18:20:44" , 
    DateTimeFormatter.ofPattern( "dd/MM/uuuu, HH:mm:ss" )  // Define a formatting pattern to match the input.
)
.atZone(                                                   // Assign a time zone to the `LocalDateTime` to create a `ZonedDateTime` object.
    ZoneId.of( "America/Los_Angeles" )                     // Specify time zone to be assigned. Always use proper zone names `continent/region`; never use 3-4 character pseudo-zones.
)

2018-03-20T18:20:44-07:00[America/Los_Angeles]

java.time

您使用的是麻烦的旧 date-time classes,现在已成为遗留问题,已被 java.time classes 取代.

将您的字符串解析为 LocalDateTime since it lacks an indicator of time zone or offset-from-UTC

String input = "20/03/2018, 18:20:44" ;
DateTimeFormatter f = DateTimeFormatter.ofPattern( "dd/MM/uuuu, HH:mm:ss" ) ;
LocalDateTime ldt = LocalDateTime.parse( input , f ) ;

ldt.toString(): 2018-03-20T18:20:44

缺少时区或 offset-from-UTC 意味着这 不是 代表一个时刻,是 不是 上的一个点时间线。如果没有 zone/offset 的上下文,这仅代表关于 26-27 小时范围内潜在时刻的模糊概念。

显然您确定此输入实际上是在某个时区。将 ZoneId 应用于此 LocalDateTime 以获得 ZonedDateTime 对象。

指定 proper time zone name in the format of continent/region, such as America/Montreal, Africa/CasablancaPacific/Auckland。切勿使用 ESTIST 等 3-4 字母缩写,因为它们 不是 真正的时区,没有标准化,甚至不是唯一的(!)。

ZoneId z = ZoneId.of( "America/Los_Angeles" ) ; 
ZonedDateTime zdt = ldt.atZone( z ) ;

转化

最好避免麻烦的遗留 classes。但是,如果您必须生成 java.util.Date 到 inter-operate 且旧代码尚未更新 java.time,则可以转换。要来回转换,请在旧 classes 上调用新方法。

A java.util.Date 表示 UTC 时间轴上的一个点,分辨率为毫秒。所以它在 java.time 中的替换是 InstantInstant 也是 UTC 时间轴上的一个点,具有更精细的纳秒分辨率。要获得 Date,我们需要一个 Instant,我们可以从 ZonedDateTime.

中提取它
Instant instant = zdt.toInstant() ;  // Same moment, same point on the timeline, different wall-clock time.

现在我们可以通过调用 Date.from.

获取遗留 class 对象 Date
java.util.Date date = Date.from( instant ) ;  // Do this only if you *must* work with `Date` class.

关于java.time

java.time framework is built into Java 8 and later. These classes supplant the troublesome old legacy date-time classes such as java.util.Date, Calendar, & SimpleDateFormat.

Joda-Time project, now in maintenance mode, advises migration to the java.time classes.

要了解更多信息,请参阅 Oracle Tutorial. And search Stack Overflow for many examples and explanations. Specification is JSR 310

您可以直接与数据库交换 java.time 对象。使用 JDBC driver compliant with JDBC 4.2 或更高版本。不需要字符串,不需要 java.sql.* classes.

从哪里获得java.time classes?

  • Java SE 8, Java SE 9,及以后
    • Built-in。
    • 标准 Java API 的一部分,带有捆绑实施。
    • Java 9 添加了一些小功能和修复。
  • Java SE 6 and Java SE 7
    • java.time 的大部分功能是 back-ported 到 Java ThreeTen-Backport 中的 6 和 7。
  • Android
    • Android java.time classes.
    • 捆绑实施的更高版本
    • 对于较早的 Android (<26),ThreeTenABP project adapts ThreeTen-Backport (mentioned above). See .

ThreeTen-Extra project extends java.time with additional classes. This project is a proving ground for possible future additions to java.time. You may find some useful classes here such as Interval, YearWeek, YearQuarter, and more.