这是我的代码:
long treatmentTimeBeginDay;
if ( effectiveBegin.after(businessClosing) ) {
LOGGER.debug("Compute treatment time for beginDay = 0: the effective begin {} is after business closing {}",
config.formatLogDate(effectiveBegin),config.formatLogDate(businessClosing));
treatmentTimeBeginDay = 0;
} else {
LOGGER.debug("Compute treatment time for beginDay between {} and {}",config.formatLogDate(effectiveBegin),config.formatLogDate(businessClosing));
treatmentTimeBeginDay = businessClosing.getTime() - effectiveBegin.getTime();
}
Preconditions.checkState( treatmentTimeBeginDay >= 0 , "Internal bug! treatmentTimeBeginDay="+treatmentTimeBeginDay );
effectiveBegin 和 businessClosing 不为空,也由 Guava 前提条件检查,您可以在日志中看到它...
在大多数情况下它运行良好,但在生产中我们有这些错误:
Caused by: java.lang.IllegalStateException: Internal bug! treatmentTimeBeginDay=-852
我不会给你剩下的堆栈/代码,因为它应该足够了...... 我的 Guava checkState 调用明确引发了异常。
我也有日志:
DEBUG [BusinessHoursUtils.java:257] llairie - Compute treatment time for beginDay between 7/19/12 8:00 PM and 7/19/12 8:00 PM
(我暂时不能和millies有log)
我想了解的是。
如果我得到我给你的日志,这意味着测试 if ( effectiveBegin.after(businessClosing) )
为假,所以 effectiveBegin 应该在或等于 businessClosing 之前。
在这种情况下,effectiveBegin 时间戳应低于 businessClosing 时间戳。
所以当我执行 businessClosing.getTime() - effectiveBegin.getTime();
时,我希望得到一个正数。
所以请有人告诉我为什么我的异常消息中有 -852 毫秒?这怎么可能?
编辑: 我怀疑一个棘手的案例,即 after/before 方法在几毫秒内不起作用,这似乎是问题所在,因为我可以在本地重现它。
运行时的 2 个日期是:
businessClosing = {java.util.Date@503}"Thu Jul 19 20:00:00 CEST 2012"
fastTime = 1342720800000
cdate = null
effectiveBegin = {java.sql.Timestamp@498}"2012-07-19 20:00:00.999"
nanos = 999000000
fastTime = 1342720800000
cdate = {sun.util.calendar.Gregorian$Date@512}"2012-07-19T20:00:00.000+0200"
有了这些运行时对象,effectiveBegin.after(businessClosing) = false
如果我在 DB 中设置 effectiveBegin = 2012-07-19 20:00:01.000,1 毫秒后,则 test = true
在这两种情况下,我都希望有 effectiveBegin.after(businessClosing) = true
看来,就像 ametren 怀疑的那样,我的约会日期不同。
那么到底是什么问题呢? 难道我们不应该能够将 2 日期实例与毫秒精度进行比较吗? 即使它们是 java.util.Date 的子类?
最佳答案
这里的问题是您混合了时间戳和日期。 Timestamp.after(Date)
只比较 Date 组件的毫秒数,它们都是 1342720800000
在你的例子中。
然而,Timestamp.getTime()
也会考虑存储在时间戳中的纳秒( 999000000ns = 999ms
)并将返回 1342720800999
.所以businessClosing.getTime() - effectiveBegin.getTime()
将返回 -999
结果。
要解决此问题,您可以将 if 语句修改为 if(effectiveBegin.compareTo(businessClosing) > 0)
或者你可以转换 businessClosingDate
到 Timestamp
在 if 语句之前。
关于时间之前的 Java 日期在生产中无法按预期工作,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11761118/