【问题标题】:How Do I Force A Specific Date Value into a Timestamp? [closed]如何强制将特定日期值放入时间戳? [关闭]
【发布时间】:2020-06-08 19:33:36
【问题描述】:

所以我有一个日期值,我必须将其转换为时间戳才能将值传递给特定方法。然而,为了完成这项工作,我被告知时间戳日期的值必须设置为 1900-01-01。

像这样的

        Date startDate = timesDate.getStartDate(); 
        Timestamp startTime = new Timestamp(startDate.getTime());

但现在我必须将日期固定为该特定值,同时保持时间不变。

编辑 - 我必须从包含设定时间的字符串的字段中提取数据。

这将是一个字段的开始时间和另一个字段的结束时间。保存时需要将字符串转换为时间戳,并且时间戳的值需要在时间值旁边以 1900-01-01 开头。

我可以回答我自己的问题吗?

【问题讨论】:

  • 您正在使用 terrible 日期时间类,这些类在几年前被 innJSR 310 定义的现代 java.time 类所取代。
  • java.util.Datejava.sql.Date?
  • @BasilBourque 好点。

标签: java date timestamp timeofday


【解决方案1】:

这是一个开始。您应该使用LocalDateLocalDateTime。这只是一种方法。可能还有其他更适合您的要求。

// your epoch
LocalDate ld =  LocalDate.of(1900,1,1);
System.out.println(ld);

// now tag on the time
LocalDateTime ldt = LocalDateTime.of(ld, LocalTime.of(2,3)); // 2:03
System.out.println(ldt);

打印

1900-01-01
1900-01-01T02:03

要标记当前时间,只需这样做。

LocalDateTime ldt = LocalDateTime.of(ld, LocalTime.now());
System.out.println(ldt);

打印

1900-01-01T16:06:50.190778200

您需要查看 DateTimeFormatter 来格式化您的应用程序的时间戳。有关最新时间功能的更多信息,请查看java.time 包。

【讨论】:

    【解决方案2】:

    tl;博士

    从旧的 java.util.Date 对象开始,更改日期,同时保持 UTC 中的时间。

    myJavaUtilDate                                 // Your `java.util.Date` object. Now legacy; avoid!
    .toInstant()                                   // Convert fromlegacy class to modern class, `Instant`.
    .atOffset( ZoneOffset.UTC )                    // Convert from basic building-block class `Instant` to the more flexible class `OffsetDateTime`. 
    .with(                                         // Move from one date to another. 
        LocalDate.of( 1900 , Month.JANUARY , 1 )   // Specify date while keeping time-of-day, and keeping the same offset-from-UTC.
    )                                              // Returns a second `OffsetDateTime` object, per immutable objects. 
    

    您可以使用 JDBC 4.2 或更高版本将生成的 OffsetDateTime 对象传递到您的数据库,而无需 Timestamp,如下所述。

    避免使用旧的日期时间类

    我被告知时间戳的日期值必须设置为 1900-01-01。

    我怀疑你对 deprecated constructor 中的 java.sql.Timestamp 的奇怪之处感到困惑,它从 1900 年开始计算年份。Javadoc 将第一个参数描述为:year - 年份减去 1900

    这将是遗留日期时间类中发现的许多棘手的设计缺陷之一。完全避免这些课程。仅使用 java.time 包中的日期时间类。

    Instant 而不是 java.util.Date

    如果给定一个java.util.Date 对象,立即转换为它的替换Instant

    Instant instant = myJavaUtilDate.toInstant() ;
    

    如果你必须产生一个java.sql.Timestamp对象时间与尚未更新到java.time的旧代码互操作,你可以转换。

    java.sql.Timestamp ts = Timestamp.from( instant ) ;
    

    您不应再使用Timestamp 与数据库交换值。 JDBC 4.2 及更高版本需要支持某些 java.time 类,包括 OffsetDateTime

    OffsetDateTime odt = instant.atOffset( ZoneOffset.UTC ) ;
    myPreparedStatement.setObject( … , odt ) ;
    

    检索。

    OffsetDateTime odt = myResultSet.getObject( … , OffsetDateTime.class ) ; 
    

    你说:

    但现在我必须将日期固定为该特定值,同时保持时间不变。

    你把我弄丢了。编辑您的问题以澄清您的问题和期望的结果。如果您指的是上面讨论的 1900 年的怪事,那么如果您使用 java.time 类按照我的代码进行操作,那就没有实际意义了。

    如果您确实想要 1900 年 1 月 1 日的日期,同时保留传递的 java.util.Date 中的时间,您必须首先了解 Date 对象代表 UTC 中的时刻。因此,如果通过另一个时区查看同一时刻,则在 UTC 中看到的时间可能会有所不同。

    我将继续假设您想要 UTC 中的时间。但是您应该编辑您的问题以澄清 UTC 与某个时区。

    LocalDate ld = LocalDate.of( 1900 , Month.JANUARY , 1 ) ;
    OffsetDateTime odt = myJavaUtilDate.toInstant().atOffset( ZoneOffset.UTC ).with( ld ) ;
    

    【讨论】:

    • 我的意思是我被告知要在时间戳上强制日期 1900-01-01 与我拉它时的时间一样。
    • @JackParker (a) 时区呢? (b) 在顶部和底部查看我的编辑。
    【解决方案3】:

    所以,您希望日期部分为1900-01-01,但时间部分为timesDate.getStartDate() 中的任何时间

    在构造新时间戳之前,您是否尝试使用 Date.set*() methods 将年、月和日设置为正确的值?

    当然,很多 Date 方法已被弃用,取而代之的是 Calendar 方法,因此更简洁的方法可能是先将 Date 转换为 Calendar 对象...或者直接使用现在有警告。

    【讨论】:

    • 这正是我想要的,我没有为每个都做 date.set,因为我认为它看起来很草率,并认为我会检查是否有我遗漏的东西。
    • 其他情况更糟。在1900-01-01 00:00:00 创建一个日期,然后运行set* 方法来复制每个时间部分?作品>优雅。如果你以后想到更好的东西,你总是可以让它变得更优雅。
    猜你喜欢
    • 2018-01-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-08-29
    相关资源
    最近更新 更多