关于显示日期,我有一个非常奇怪的问题。特别是在Windows中。我不知道为什么,当我从查询中获得一个日期(Hibernate)时,它给了我一天的时间。当数据到达服务器时,日期很好但是当它到达客户端时它会减少一天。例如:在服务器中,日期为 Fri Sep 24 00:00:00 1982 ,但是当它到达客户端时 Thu Sep 23 23:00:00 1982 。正如你可以看到它的一个不同的一天。
啊,我差点忘了提到它发生在Windows(Seven)上,因为它的TimeZone是UTC而不是GMT。我和我的同事使用Linux,没有问题。
有没有解决方法呢?
提前致谢!
答案 0 :(得分:3)
之前没有给你一个天的价值。它提前给你一个小时的值(9月24日午夜和9月23日晚上11点)。
这几乎肯定是一个时区问题,这几乎肯定只是你如何格式化日期的反映。如果您使用SimpleDateFormatter
,只需适当设置TimeZone
(您的实际要求将确定哪个区域),您应该得到相同的结果。
顺便说一句,一般来说,我建议尽可能使用Joda Time来说明Java中的日期/时间工作 - 它比Date
和{{1}更清晰的API }。
答案 1 :(得分:2)
与Jon Skeet correctly points一样,您可能遇到了时区问题。您的中间件工具可能正在动态地应用默认时区,这是一个很好的意图,但非常令人困惑的反功能。
现代的解决方案是使用添加到Java 8及更高版本中的 java.time 类。
从JDBC 4.2开始,我们可以与数据库交换 java.time 对象。 Hibernate和JPA已更新,可以处理 java.time 。
从类似于TIMESTAMP WITH TIME ZONE
的列中检索。
OffsetDateTime odt = myResultSet.getObject( … , OffsetDateTime.class ) ;
写作。
myPreparedStatement.setObject( … , odt ) ;
通过使用这些对象,您将避免中间件工具应用时区。使用JDBC 4.2检索 java.time 对象,您将看到真正存储的值。
java.time框架已内置在Java 8及更高版本中。这些类取代了麻烦的旧legacy日期时间类,例如java.util.Date
,Calendar
和SimpleDateFormat
。
要了解更多信息,请参阅Oracle Tutorial。并在Stack Overflow中搜索许多示例和说明。规范为JSR 310。
Joda-Time项目(现在位于maintenance mode中)建议迁移到java.time类。
您可以直接与数据库交换 java.time 对象。使用符合JDBC driver或更高版本的JDBC 4.2。不需要字符串,不需要java.sql.*
类。
在哪里获取java.time类?
ThreeTen-Extra项目使用其他类扩展了java.time。该项目为将来可能在java.time中添加内容打下了基础。您可能会在这里找到一些有用的类,例如Interval
,YearWeek
,YearQuarter
和more。