【问题标题】:How to convert java date without Z to a date with Z如何将不带 Z 的 java 日期转换为带 Z 的日期
【发布时间】:2016-02-18 09:55:09
【问题描述】:

我有以下日期值 1995-12-31T23:59:59

但为了将其解析为 solr 查询,我需要以下格式

1995-12-31T23:59:59Z

如何解析这个以在 java 1.6 的末尾添加“Z”?

转换后的类型必须是 java.util.date - fyi

当我现在 toString 日期并尝试使用 SimpleDateFormat 对象解析它时,它看起来像这样

“Mon Jan 01 00:00:00 CST 2001” - 转换它的格式是什么?

【问题讨论】:

  • 请记住,“Z”字符表示它是 UTC 时间,因此您可能需要执行必要的区域转换

标签: java datetime


【解决方案1】:

使用 SimpleDateFormat:

  SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'");
  Date d = df.parse("1995-12-31T23:59:59Z");
  System.out.println(d);

将“Z”放在单引号中以进行转义

【讨论】:

  • 根据这个answer,Z应该有自己的含义。所以我不确定这是 OP 想要的。
  • 阅读!将 Z 括在单引号中,它将被转义。 Z 指的是时区,但一些 xml 表示会附加一个随机 Z 以增加您的解析乐趣。如果 OP 的实际日期字符串具有时区偏移量(a la -0700),那么他/她应该取消引用 Z 并且它将被解析为数字时区偏移量,否则如果它是 OP 的问题他/她的实际“Z”应该以单引号括起来的格式包含它。
【解决方案2】:

“Z”是祖鲁时区的时区缩写,即UTC。如果 solr API 接受日期对象,那么您可以通过设置首选时区以以下方式解析日期:

SimpleDateFormat dateParser = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss");
dateParser.setTimeZone(TimeZone.getTimeZone("Z"));
Date date = df.parse("1995-12-31T23:59:59");

如果需要转回字符串则使用nsfyn55提供的方法:

SimpleDateFormat dateFormatter = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'");
System.out.println(dateFormatter.format()); 

【讨论】:

【解决方案3】:

避免使用旧的日期时间类

您正在使用旧的 java.util.Date/.Calendar 和 SimpleDateFormat 类。避开他们。

Date 类的 toString 在生成字符串时应用默认时区的设计选择不佳。因此,它似乎有一个时区,而实际上却没有(除了埋在下面的一个时区,它被忽略以供常规使用)。令人困惑,是的。避免它。

java.time

改为使用 Java 8 及更高版本中内置的 java.time。

首先解析为LocalDateTime,不带任何时区或偏移量。

LocalDateTime ldt = LocalDateTime.parse( "1995-12-31T23:59:59Z" );

应用time zoneoffset-from-UTC 赋予LocalDateTime 含义,使其成为时间轴上的实际时刻。您必须知道或询问该字符串打算使用的时区或偏移量,因为没有嵌入任何指示。对于这个例子,我将任意假设Québec

ZoneId zoneId = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = ldt.atZone( zoneId );

您想要的输出末尾有一个Z,对于Zulu,这意味着UTC

在 java.time 中,Instant 代表 UTC 时间线上的一个时刻。您可以从ZonedDateTime 中提取Instant

Instant instant = zdt.toInstant();

Instant 类的 toString 方法会生成您所需格式的字符串。该格式是标准ISO 8601 格式之一。

String output = instant.toString();

半开

我碰巧注意到您的示例值试图获得 1995 年底。有更好的方法来执行此类搜索或比较标准。

在日期时间工作中,最佳实践称为半开放式,其中时间跨度的开始是包含,而结束是不包含。因此,一周从星期一开始,一直持续到但不包括下星期一。

定义年份是指从 1995 年第一天的第一刻开始,一直到但不包括下一年,即 1996 年第一天的第一刻。搜索任何值在该范围内不是使用 BETWEEN 而是作为:( someEvent >= firstMomentOf1995 AND someEvent < firstMomentOf1996 )(不是

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2021-07-03
    • 2012-02-28
    • 2013-05-07
    • 2020-04-16
    • 2020-09-24
    • 2013-07-15
    • 2012-08-12
    • 2019-05-30
    相关资源
    最近更新 更多