在保持时区不变的同时阅读,编写和序列化日期和时间变得令人讨厌。我正在使用Ruby(和Rails 3.0)并试图改变DateTime的时区。 (到UTC)但不是时间本身。
我想要这个:
t = DateTime.now
t.hour
-> 4
t.offset = 0
t.hour
-> 4
t.utc?
-> true
我最接近的是这个,但它并不直观。
t = DateTime.now
t.hour
-> 4
t += t.offset
t = t.utc
t.hour
-> 4
t.utc?
-> true
还有更好的方法吗?
答案 0 :(得分:37)
使用Rails 3,您正在寻找DateTime.change()
dt = DateTime.now
=> Mon, 20 Dec 2010 18:59:43 +0100
dt = dt.change(:offset => "+0000")
=> Mon, 20 Dec 2010 18:59:43 +0000
答案 1 :(得分:9)
使用数字偏移,例如由于夏令时,'+1000'不会全年工作。 Checkout ActiveSupport :: TimeZone。 More info here
答案 2 :(得分:8)
我会改用Time对象。因此,获取当前本地时间,然后将其增加UTC偏移量并转换为UTC,如下所示:
t = Time.now # or Time.parse(myDateTime.asctime)
t # => Thu Dec 16 21:07:48 -0800 2010
(t + t.utc_offset).utc # => Thu Dec 16 21:07:48 UTC 2010
虽然根据Phrogz评论,如果您只想以独立于位置的方式存储时间戳,那么只需使用当前的UTC时间:
Time.now.utc
答案 3 :(得分:8)
d = DateTime.now
puts [ d, d.zone ]
#=> 2010-12-17T13:28:29-07:00
#=> -07:00
d2 = d.new_offset(3.0/24)
puts d2, d2.zone
#=> 2010-12-17T23:28:29+03:00
#=> +03:00
修改:此答案不会考虑通过评论另一个答案提供的信息,即希望在时区更改后报告的“小时”相同。
答案 4 :(得分:3)
正如 @Sam 指出的那样,更改偏移量是不够的,并且会导致错误。为了抵抗DST时钟的进步,转换应按以下方式进行:
d = datetime_to_alter_time_zone
time_zone = 'Alaska'
DateTime.new
.in_time_zone(time_zone)
.change(year: d.year, month: d.month, day: d.day, hour: d.hour, min: d.min, sec: d.sec)
答案 5 :(得分:1)
如果有人(像我一样)的字符串格式为时区,例如“太平洋时间(美国和加拿大)”
这是我找到的最佳方式:
datetime.change(ActiveSupport::TimeZone[time_zone_string].formatted_offset(false)
答案 6 :(得分:-1)
您可以通过在配置文件(config / application.rb)中添加以下行来指定要在应用中使用的时区: config.time_zone ='孟买'
您可以在此处找到相同的官方文档:http://api.rubyonrails.org/classes/ActiveSupport/TimeZone.html
另一个选择是你“猴子补丁”“日期时间”类。