铁轨时间是午夜中断的吗?



让我们看看日期:

1.9.2p320 :008 > Date.today
=> Wed, 03 Oct 2012 
1.9.2p320 :009 > Time.now
=> 2012-10-03 22:32:55 -0400

现在,鉴于午夜是什么时候?

1.9.2p320 :005 > Date.today.midnight
=> Wed, 03 Oct 2012 00:00:00 UTC +00:00 

意义。但是昨天呢?

1.9.2p320 :006 > Date.yesterday.midnight
=> Wed, 03 Oct 2012 00:00:00 UTC +00:00 

呃,这不太有意义。今天的午夜和昨天的午夜一样吗?你不能当真!

1.9.2p320 :026 > Date.today.midnight == Date.yesterday.midnight
=> true 
1.9.2p320 :033 > 1.day.ago.midnight == Date.yesterday.midnight
=> true 
1.9.2p320 :034 > 1.day.ago.midnight == Date.today.midnight
=> true 

哦,你是认真的。明天呢?

1.9.2p320 :007 > Date.tomorrow.midnight
=> Fri, 05 Oct 2012 00:00:00 UTC +00:00 

等等,如果今天午夜是3号00:00,昨天的午夜是3号的00:00,但明天的午夜是5号的00:00,那么4号的00:00在哪里?

在这里:

1.9.2p320 :010 > 0.days.ago
=> Thu, 04 Oct 2012 02:34:58 UTC +00:00 
1.9.2p320 :011 > 0.days.ago.midnight
=> Thu, 04 Oct 2012 00:00:00 UTC +00:00

但零天前不是今天吗?显然不是。

是我,还是这根本不是内在一致的?在我看来,Date.today 应该与 0.days.ago 相同。

我知道days.ago实际上是在使用 Time 对象,这是一个时区问题:

1.9.2p320 :030 > Date.today
=> Wed, 03 Oct 2012 
1.9.2p320 :021 > Time.now
=> 2012-10-03 22:40:09 -0400 
1.9.2p320 :023 > 0.days.ago
=> Thu, 04 Oct 2012 02:40:22 UTC +00:00 
1.9.2p320 :022 > Time.zone.now
=> Thu, 04 Oct 2012 02:40:14 UTC +00:00 

但似乎,鉴于这些是便利函数,将时区假设扔到一个便利函数中而不是将其扔到另一个便利函数中是一种意思,从所有角度来看,这两者都意味着同样的事情。

即使撇开这一点,它似乎也无法解释Date.today.midnight == Date.yesterday.midnight的事实,很简单,就是发疯。

既然我知道我不可能是第一个被这个咬伤的人,我问我错过了什么?

Rails 将基于相对日期计算,例如yesterdaytomorrowmidnightDate.current,这些计算将尝试使用配置的Time.zone: https://github.com/rails/rails/blob/master/activesupport/lib/active_support/core_ext/date/calculations.rb#L46

由于您的Time.zone设置为 UTC,因此您不会获得与基于Date.today的计算相同的结果,这将使用计算机的时钟时间,除非您实际上处于 UTC 时间。

因此,如果您和 UTC 之间的时差大于午夜的时间,则Date.yesterdayDate.today实际上返回相同的日期!

尝试使用Time.zone = 'Eastern Time (US & Canada)'或您所在的任何时区设置您的 Rails 时区,然后重试您的示例。

罗斯塔确定了罪魁祸首。如有必要,您可能会Time.now.to_date并指定时区:

> Time.now.in_time_zone("Asia/Tokyo")
=> Thu, 04 Oct 2012 12:54:43 JST +09:00 
> Time.now.in_time_zone("Asia/Tokyo").to_date.midnight
=> Thu, 04 Oct 2012 00:00:00 JST +09:00 
Time.now.in_time_zone("Asia/Tokyo").to_date.yesterday.midnight
=> Wed, 03 Oct 2012 00:00:00 JST +09:00 
> Time.zone = "America/Los_Angeles"
=> "America/Los_Angeles" 
> Time.now.in_time_zone
=> Wed, 03 Oct 2012 20:55:35 PDT -07:00 
> Time.now.to_date # using the system time
=> Wed, 03 Oct 2012 
> Time.now.to_date.midnight
=> Wed, 03 Oct 2012 00:00:00 PDT -07:00 
> Time.now.to_date.yesterday.midnight
=> Tue, 02 Oct 2012 00:00:00 PDT -07:00 

相关内容

  • 没有找到相关文章

最新更新