使用冒号分隔符格式化ISO 8601日期

时间:2015-04-15 08:15:58

标签: java date iso8601

我正在尝试将日期(以毫秒为单位)转换为以下ISO 8601格式:

enter image description here

但是我使用SimpleDateFormat获得以下内容:

    /**
     * It converts the time from long to the ISO format
     * 
     * @param timestampMillis
     * @return isoDate
     */
    public String convertTimeMillisToISO8601(String timestampMillis)
    {
        long timeInLong= Long.parseLong(timestampMillis);
        DateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssZ");
        df.setTimeZone(TimeZone.getTimeZone("UTC"));
        String isoDate = df.format(new java.util.Date(timeInLong));
        return isoDate;
    }

输出:

"ts":"2015-06-18T09:56:21+0000"

我知道我可以使用子字符串来附加额外的冒号但是有没有更好的方法呢?

5 个答案:

答案 0 :(得分:5)

对于Java 7及更高版本,您可以在日期格式String中使用XXX(ISO 8601时区)。根据{{​​3}},X的结果可以是:

X    => -08
XX   => -0800
XXX  => -08:00

但是对于所有这些,它也可以返回Z

对于Java 6及更早版本,没有Xthe documentation),由于X的结果可能会或可能不会达到您想要的效果,我强烈建议您只需插入结肠自己。

答案 1 :(得分:1)

您可以随时use a StringBuilder

new StringBuilder(
      new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssZ")
      .format(date))
    .insert(22,':')
    .toString();

答案 2 :(得分:0)

你能使用Java 8吗?

DateTimeFormatter formatter = DateTimeFormatter.ofPattern("YYYY-MM-dd'T'HH:mm:ssXXX");
System.out.println(formatter.format(ZonedDateTime.now()));
  

2015-04-15T17:24:19 + 09:00

答案 3 :(得分:0)

对于Java 8,如果您使用标准的ISO_DATE_*格式模式之一,则当偏移量为+00:00时,输出格式的字符串将被截断(UTC通常仅追加{{ 1}})。

Z

我发现的唯一解决方案是使用{<1>}(如下所示),该{<1>小写“ xxx”确保时区偏移量中包含冒号。

为了完整起见,我提供了一个示例,其中包含一秒钟的派系(您可以删除OffsetDateTime utcWithFractionOfSecond = ZonedDateTime.parse("2018-01-10T12:00:00.000000+00:00", DateTimeFormatter.ISO_OFFSET_DATE_TIME); utcWithFractionOfSecond.format(DateTimeFormatter.ISO_OFFSET_DATE_TIME); // 2018-01-10T12:00:00Z ... not what you want!

outputPattern

在这些示例中,我仅使用ISO_OFFSET_DATE_TIME创建测试用例的输入值。在所有情况下,由outputPattern SSSSSS控制如何在生成的格式化字符串的时区部分中包含冒号。

请注意,如果输入数据包含区域ID,例如DateTimeFormatter inputPattern = DateTimeFormatter.ISO_OFFSET_DATE_TIME; DateTimeFormatter outputPattern = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss.SSSSSSxxx"); OffsetDateTime utcWithFractionOfSecond = OffsetDateTime.parse("2018-01-10T12:00:00.000000+00:00", inputPattern); OffsetDateTime utcNoFractionOfSecond = OffsetDateTime.parse("2018-01-10T12:00:00+00:00", inputPattern); OffsetDateTime utcWithZ = OffsetDateTime.parse("2018-01-10T12:00:00Z", inputPattern); OffsetDateTime utcPlus3Hours = OffsetDateTime.parse("2018-01-10T12:00:00.000000+03:00", inputPattern);| utcWithFractionOfSecond.format(outputPattern ); // 2018-01-10T12:00:00.000000+00:00 utcNoFractionOfSecond.format(outputPattern); // 2018-01-10T12:00:00.000000+00:00 utcWithZ.format(outputPattern); // 2018-01-10T12:00:00.000000+00:00 utcPlus3Hours.format(outputPattern); // 2018-01-10T12:00:00.000000+03:00 ,则可以使用ZonedDateTime而不是OffsetDateTime

创建输入数据

答案 4 :(得分:0)

tl; dr

OffsetDateTime.parse( "2014-06-18T09:56:21+00:00" )
  

2014-06-18T09:56:21Z

详细信息

使用现代的 java.time 类替代了可怕的旧遗留类(DateCalendarSimpleDateFormat )。但是他们要么工作太努力,要么选择了错误的课程。

ISO 8601

您的格式为标准ISO 8601格式。在解析/生成表示日期和时间值的文本时,默认情况下, java.time 类使用这些标准格式。因此,您根本不需要指定任何格式模式。默认情况下有效。

OffsetDateTime

您的输入指示offset-from-UTC为零小时零分钟。因此,我们应该使用OffsetDateTime类。

String input = "2014-06-18T09:56:21+00:00";
OffsetDateTime odt = OffsetDateTime.parse( input );

祖鲁时间

我们只需调用toString就可以生成标准ISO 8601格式的字符串。最后的Z表示UTC,并发音为“ Zulu”。

  

odt.toString():2014-06-18T09:56:21Z

ZonedDateTime

如果您输入的内容显示的是时区,而不仅仅是偏移量,我们将使用ZonedDateTime类。偏移量只是几个小时,几分钟和几秒钟,仅此而已。时区多了 个。时区是特定区域的人们过去,现在和将来对偏移量的更改的历史记录。


关于 java.time

java.time框架已内置在Java 8及更高版本中。这些类取代了麻烦的旧legacy日期时间类,例如java.util.DateCalendarSimpleDateFormat

目前位于Joda-Timemaintenance mode项目建议迁移到java.time类。

要了解更多信息,请参见Oracle Tutorial。并在Stack Overflow中搜索许多示例和说明。规格为JSR 310

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

在哪里获取java.time类?

ThreeTen-Extra项目使用其他类扩展了java.time。该项目为将来可能在java.time中添加内容提供了一个试验场。您可能会在这里找到一些有用的类,例如IntervalYearWeekYearQuartermore