【问题标题】:how to convert dateTime type to gregorianCalendar如何将 dateTime 类型转换为 gregorianCalendar
【发布时间】:2012-06-03 19:36:00
【问题描述】:

我在字符串中获取时间,例如“2011-02-27T10:03:33.099-06:00”,它属于 xml dateTime 类型。我也有 TimeZone 类型的时区。我应该如何在该时区将 dateTime 转换为 GregorianCalendar java 类型。

【问题讨论】:

标签: java datetime gregorian-calendar


【解决方案1】:

Java 已内置代码来解析 xml 日期时间:使用 DatatypeConverter.parseDateTime()。这将在解析的 TimeZone 中返回一个日历。然后,您可以将 Calendar TimeZone 设置为所需的目标 TimeZone,以执行您接下来需要执行的任何操作。

【讨论】:

    【解决方案2】:
    sdf = new java.text.SimpleDateFormat ("yyyy-MM-dd'T'HH:mm:ss.S");
    

    解析除尾随 TZ 之外的所有内容。

    sdf.parse (sd);
    res168: java.util.Date = Sun Feb 27 10:03:33 CET 2011
    

    来自api docs,我期待

    sdf = new java.text.SimpleDateFormat ("yyyy-MM-dd'T'HH:mm:ss.SSSz");
    

    用来读取-06:00到底。但我看到,要么存在预期的 0700 形式的偏移量,要么存在 GMT 前缀,例如“GMT-04:00”。所以你必须自己插入那个 GMT-thingy:

    sdf.parse (sd.replaceAll ("(......)$", "GMT$1"))
    

    SDF.parse(str) 返回一个Date,需要转换成GC:

    GregorianCalendar calendar = new GregorianCalendar ();
    calendar.setTime (date);
    

    【讨论】:

    • 执行此操作时出现解析异常: SimpleDateFormat sDF = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.Sz");日期 resultDate = sDF.parse("2012-02-27T10:03:33.099-06:00");
    • @vjk: 是的,它必须是resultDate = sDF.parse("2012-02-27T10:03:33.099-06:00".replaceAll("(......)$", "GMT$1"));,其中 a) 在时间偏移之前插入 GMT,最后将秒“SSSz”的分数插入 3 个位置。
    • 在 Java 7 中,您现在可以使用“X”而不是“Z”,后者使用 ISO 8601 时区格式(例如 -06、-0600、-06:00)。
    【解决方案3】:

    tl;博士

    OffsetDateTime.parse( "2011-02-27T10:03:33.099-06:00" )
    

    java.time

    现代方法使用 java.time 类取代了麻烦的旧旧日期时间类。具体来说,GregorianCalendarZonedDateTime 替换为时区,OffsetDateTime 被替换为仅与 UTC 的偏移量。

    ISO 8601

    您的输入字符串恰好符合ISO 8601 标准格式。

    java.time 类在解析/生成字符串时默认使用这些标准格式。所以不需要指定格式模式。

    OffsetDateTime

    您的输入字符串包含offset-from-UTC,但不包含time zone。所以解析为OffsetDateTime

    OffsetDateTime odt = OffsetDateTime.parse( "2011-02-27T10:03:33.099-06:00" ) ;
    

    ZonedDateTime

    如果您确定预期的时区,请应用ZoneId 以生成ZonedDateTime

    时区总是比单纯的偏移更可取。区域是特定区域的人们使用的偏移量的过去、现在和未来变化的历史。

    continent/region 的格式指定proper time zone name,例如America/MontrealAfrica/CasablancaPacific/Auckland。切勿使用 3-4 个字母的缩写,例如 ESTIST,因为它们不是真正的时区,没有标准化,甚至不是唯一的 (!)。

    ZoneId z = ZoneId.of( "Pacific/Galapagos" ) ;  
    ZonedDateTime zdt = odt.atZoneSameInstant( z ) ;
    

    转换传统 ↔ 现代

    如果您必须有一个GregorianCalendar 对象才能与尚未更新到java.time 的旧代码互操作,则可以转换。查看添加到旧类的新方法。

    GregorianCalendar myGregCal = GregorianCalendar.from( zdt ) ;
    

    然后往另一个方向发展……

    ZonedDateTime zdt = myGregCal.toZonedDateTime() ;
    


    关于java.time

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

    Joda-Time 项目现在位于maintenance mode,建议迁移到java.time 类。

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

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

    从哪里获得 java.time 类?

    ThreeTen-Extra 项目通过附加类扩展了 java.time。该项目是未来可能添加到 java.time 的试验场。您可以在这里找到一些有用的类,例如IntervalYearWeekYearQuartermore

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-08-26
      • 2010-11-12
      • 2020-12-06
      • 1970-01-01
      • 2023-03-06
      相关资源
      最近更新 更多