如何在一个DateTimeFormater Java 8中处理所有区域偏移 [英] How to handle all Zone Offset in one DateTimeFormater Java 8

查看:309
本文介绍了如何在一个DateTimeFormater Java 8中处理所有区域偏移的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我需要为以下有效日期创建 DateTimeFormatter

I need to create a DateTimeFormatter for the following valid dates.

  String date1 = "2017-06-20T17:25:28";
  String date2 = "2017-06-20T17:25:28.477777";
  String date3 = "2017-06-20T17:25:28.477777Z";
  String date4 = "2017-06-20T17:25:28.477777UTC";
  String date5 = "2017-06-20T17:25:28.477777-05";
  String date6 = "2017-06-20T17:25:28.477777+05";
  String date7 = "2017-06-20T17:25:28.477777+05:30";
  String date8 = "2017-06-20T17:25:28.477777-05:30";
  String date9 = "2017-06-20T17:25:28.477777+0530";
  String date10 = "2017-06-20T17:25:28.477777-0530";

我已经尝试过以下日期时间格式化程序,但最后两个日期失败( date9 date10 )。

I have tried the following date time formatter, but this fails for last two dates (date9, date10).

private static final DateTimeFormatter DATE_TIME_FORMATTER = new DateTimeFormatterBuilder()
    .appendPattern("yyyy-MM-dd'T'HH:mm:ss")
    .appendFraction(ChronoField.MICRO_OF_SECOND, 0, 6, true)
                        .optionalStart().appendZoneId().optionalEnd()
                        .optionalStart().appendOffset("+HH", "+00").optionalEnd()
                        .optionalStart().appendOffset("+HH:mm", "+00:00").optionalEnd()
                        .optionalStart().appendOffset("+HHmm", "+0000").optionalEnd().toFormatter();

所有日期从 date1 date8 工作正常但我在尝试解析最后两个日期时得到 DateTimeParseException

All dates from date1 to date8 work fine but I get a DateTimeParseException when trying to parse last two dates:


线程main中的异常java.time.format.DateTimeParseException:无法解析文本2017-06-20T17:25:28.477777 + 0530,在索引29处找到未解析的文本

Exception in thread "main" java.time.format.DateTimeParseException: Text '2017-06-20T17:25:28.477777+0530' could not be parsed, unparsed text found at index 29

用于解析我正在使用的日期。

For parsing the date I am using following.

LocalDateTime.parse(date1, DATE_TIME_FORMATTER);

抵消的有效模式来自 OffsetIdPrinterParser

static final class OffsetIdPrinterParser implements DateTimePrinterParser {
        static final String[] PATTERNS = new String[] {
            "+HH", "+HHmm", "+HH:mm", "+HHMM", "+HH:MM", "+HHMMss", "+HH:MM:ss", "+HHMMSS", "+HH:MM:SS",
        };  // order used in pattern builder

我在使用有效的ZoneOffset模式时无法理解为什么我的最后两个日期失败。

I am not able to understand while I am using valid ZoneOffset patterns, why my last two dates fail.

推荐答案

另一种选择是使用由 []分隔的可选部分,以及相应的偏移模式 VV x ):

Another alternative is to use optional sections, delimited by [], and the respective offset patterns (VV and x):

DATE_TIME_FORMATTER = DateTimeFormatter
                         // pattern with optional sections: fraction of seconds and offsets
                         .ofPattern("yyyy-MM-dd'T'HH:mm:ss[.SSSSSS][VV][x][xx][xxx]");

每对 [] 相当于一个 optionalStart optionalEnd 部分。请注意,我还必须将大写 S (小数秒)包含为可选项,以解析此字段不存在的情况。

Each pair of [] is equivalent to one optionalStart and optionalEnd section. Note that I also had to include the uppercase S (fraction of second) as optional, to parse the case where this field is not present.

其他模式( VV x )对应于您需要的各种偏移量。来自 javadoc

The other patterns (VV and x) correspond to the various offsets you need. From the javadoc:

Pattern  Count  Equivalent builder methods
-------  -----  --------------------------
  VV      2      appendZoneId()
  x       1      appendOffset("+HHmm","+00")
  xx      2      appendOffset("+HHMM","+0000")
  xxx     3      appendOffset("+HH:MM","+00:00")

这适用于所有输入日期。

This works for all your input dates.

唯一的区别是 [。SSSSSS] 接受完全 6位数分数秒字段(或零数字,因为它是可选部分),而 appendFraction 接受任意数量 0到6位数。要获得完全相同的行为,您必须使用 DateTimeFormatterBuilder

The only difference is that [.SSSSSS] accepts exactly 6 digits in the fraction-of-seconds field (or zero digits, as it's an optional section), while appendFraction accepts any quantity from 0 to 6 digits. To get exactly this same behaviour, you must use the DateTimeFormatterBuilder:

DATE_TIME_FORMATTER = new DateTimeFormatterBuilder()
    // date and time
    .appendPattern("yyyy-MM-dd'T'HH:mm:ss")
    // fraction of seconds, from 0 to 6 digits
    .appendFraction(ChronoField.MICRO_OF_SECOND, 0, 6, true)
    // optional offset patterns
    .appendPattern("[VV][x][xx][xxx]")
    .toFormatter();

这篇关于如何在一个DateTimeFormater Java 8中处理所有区域偏移的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆