如何比较java.sql.Timestamp和java.util.Date

时间:2017-05-10 03:03:39

标签: java mysql date java-6 sql-timestamp

我知道java Date的设计很差,但直到今天我还不知道。

我将日期保存到数据库中,当我从数据库中获取并与原始日期进行比较时,它告诉我它的不同之处!

我写了一个看起来很奇怪的测试,但它已经通过了!

@Test
public void date_equals() {
    Date now = new Date();
    Timestamp timestamp = new Timestamp(now.getTime());

    assertFalse(timestamp.equals(now));
    assertTrue(now.equals(timestamp));

    assertTrue(timestamp.compareTo(now) == 0);
    assertFalse(now.compareTo(timestamp) == 0);

    assertTrue(timestamp.getTime() == now.getTime());
    assertTrue(now.getTime() == timestamp.getTime());
}

我注意到java.sql.Timestamp与Date有一点不同,大概是纳秒,我不在乎。

有谁能告诉我如何在最佳实践中比较这两个? 我不想在任何地方比较日期使用getTime(),是否有任何公共库或其他方法来执行此操作?

BTW我正在使用JDK 6

2 个答案:

答案 0 :(得分:5)

TL;博士

originalInstant.equals( 
    DateTimeUtils.toInstant( mySqlTimestamp ) 
) 

避免遗留日期时间类

与最早版本的Java捆绑在一起的旧日期时间类是一个非常混乱,设计不佳和笨拙的黑客。其中一个糟糕的做法是让java.sql.Timestamp成为java.util.Date的子类,同时告诉你忽略继承的事实。

引用the class doc(强调我的):

  

由于Timestamp类和上面提到的java.util.Date类之间的差异,建议代码不要将Timestamp值一般视为java.util.Date 的实例。 Timestamp和java.util.Date之间的继承关系实际上表示实现继承,而不是类型继承。

你被告知假装他们不是相关课程。因此,您尝试比较每种类型的对象是不合适的。

数据丢失

Timestamp的分辨率最高为nanosecondsjava.util.Date课程仅限于milliseconds。所以这两者不会相等。

使用java.time

相反,请使用java.time类。它们的大部分功能都可以作为Java 6的后端 - 见下文。

获得Timestamp后,立即转换为java.time类型。在Java 8及更高版本中,您可以调用添加到旧类中的新方法进行转换。在Java 6& 3的ThreeTen-Backport库中。 7,使用org.threeten.bp.DateTimeUtils.toInstant( Timestamp )

InstantUTC中时间轴上的一个时刻,分辨率为nanoseconds

Instant instant = DateTimeUtils.toInstant( mySqlTimestamp ) ;

现在与原始Instant进行比较。

boolean isOriginal = originalInstant.equals( instant ) ;

关于java.time

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

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

要了解详情,请参阅Oracle Tutorial。并搜索Stack Overflow以获取许多示例和解释。规范是JSR 310

从哪里获取java.time类?

答案 1 :(得分:1)