为什么我不应该使用 date4j 而不是 joda java.util.Calendar 或 jsr 310?



我最近遇到了date4j,这是一个非常简单的库(本质上是一个类),用于在Java中处理日期。从概念上讲,我非常喜欢date4j的"想法"。事实上,在阅读了整个主站点和javadoc中的文档之后,我非常同意上面所说的一切。

现在,可能有几个我不应该使用date4j的原因——bug、性能、缺少用户等等。我不是在问那些事情。我在问,从概念上讲,date4j的想法有什么问题(对于大多数应用程序来说)?当然,可能会有一些应用程序需要joda或three之类的东西,但我相信这只是少数。

对于处理日期/时间的用户(几乎每个编写java应用程序的人),通常给出的建议是这样的:

  • 使用joda-time代替java.util.Calendar
  • 设置web服务器为UTC
  • 设置数据库服务器为UTC
  • 以UTC格式存储日期时间

事实上,最后三个要点说明了人们在处理日期时当前心理模型的问题。人们试图在应用程序和数据库级别管理时区(更不用说ORM框架增加了另一层抽象,使事情进一步复杂化)。

你不应该做那些事。如果使用java.util。例如,日历,并且您正在操作某个用户定义的时区中的时间:

Calendar c = Calendar.getInstance(TimeZone.getTimeZone("America/New_York"));
c.set(Calendar.YEAR, 2011);
c.set(Calendar.MONTH, 0);
c.set(Calendar.DAY_OF_MONTH, 1);
c.set(Calendar.HOUR_OF_DAY, 3);
c.set(Calendar.MINUTE, 0);
c.set(Calendar.SECOND, 0);
c.set(Calendar.MILLISECOND, 0);

表示时间上的"瞬间",与时区无关。您应该能够在数据库之间进行持久化,而不必担心发生任何类型的"转换"。如果数据库在上海时区,而web服务器在洛杉矶时区,这应该无关紧要——无论如何,在时间上的瞬间是相同的。

一个问题是一些数据库试图为你管理时区(我看着你,Postgres!grr!),更糟糕的是,JDBC驱动程序级别的行为是特定于供应商的——即PreparedStatement.setDate/getDate。

date4j使用的心智模型似乎消除了所有的困惑。例如,在调用now()时显式强制用户提供时区。网站上有一些关于使用库的非常好的建议(这些事情我之前已经在我自己的应用程序中做过),例如:

  • 不要使用试图管理时区的数据库类型
  • 将时区存储为单独的列(如果需要)

为什么没有更多的人采用像date4j这样的库?

我从来没有看过date4j直到现在,但我通读了文档,我有一个具体的问题,和一个意见,什么是错误的。

首先,具体问题。它内部不维护Timezone。因此,日光节约时间存在模糊性。考虑一下周日凌晨1:59:59(美国东部时间)变为凌晨1:00:00(美国东部时间)的过渡。显然,在那一天,说凌晨1:30是模棱两可的。这个时间发生两次。所以下面是有歧义的

new DateTime("2011-11-06 01:30:00")
第二,我的观点。Date的问题是它不维护时区。等到Calendar出现的时候,损害已经造成了。此外,Calendar本身的可变性也没有给自己带来任何好处。但从本质上讲,解决方案不仅要包括时间,还要包括被感知的地方——时区、文化、地点之类的东西。然后需要在持久化到数据库、序列化、通信等过程中维护这些数据。同样的个人原则使我谦虚地建议,即使xsd:dateTime也不够,因为它只是允许相对于UTC表示日期+时间,它没有规定是否,例如,正在观察夏令时

四年后,我遇到了这个问题。对我来说,date4j的第一个问题是bug。我知道你没有特别问这些,但这是一个大问题。

更具体地说,bug本身并不是问题,是完全没有某种bug报告系统让我对date4j感到困扰。甚至没有邮件列表,据我所知,什么都没有。我知道这对于讨论日期/时间API应该是什么样子可能不是很有趣,但是基础设施仍然是重要的。

缺乏一个库很可能是一个库没有被广泛采用的原因

相关内容

  • 没有找到相关文章

最新更新