Câu hỏi Làm thế nào để tôi chuyển đổi DateTime.now thành UTC trong Ruby?


Nếu tôi có d = DateTime.now, làm thế nào để chuyển đổi 'd' thành UTC (với ngày thích hợp)?


75
2018-04-16 11:15


gốc




Các câu trả lời:


d = DateTime.now.utc

Rất tiếc!

Điều đó dường như làm việc trong Rails, nhưng không phải vani Ruby (và tất nhiên đó là câu hỏi đang hỏi)

d = Time.now.utc

Tuy nhiên, công việc có hiệu quả không.

Có lý do nào bạn cần sử dụng không DateTime và không Time? Time nên bao gồm mọi thứ bạn cần:

irb(main):016:0> Time.now
=> Thu Apr 16 12:40:44 +0100 2009

120
2018-04-16 11:17



Bởi vì tôi muốn ngày chính xác cho việc chuyển đổi, tức là, đối với GMT +10 có thể tiến lên vào ngày hôm sau ... - Ash
Thời gian sẽ làm điều đó cho bạn tốt. Thời gian cũng bao gồm cả phần ngày, không chỉ là thời gian trong ngày. Do Time.now.inspect để có một cái nhìn. - DanSingerman
Oh ngọt ngào. Vì vậy, whats sự khác biệt giữa ngày, thời gian và DateTime sau đó? - Ash
Thời gian được lưu trữ nội bộ dưới dạng số giây và micro giây kể từ kỷ nguyên, ngày 1 tháng 1 năm 1970 00:00 giờ UTC. Ngày tháng, nội bộ, được biểu diễn như một Số ngày thiên văn Julian, và DateTime chỉ đơn giản là lạ (có lẽ đó là lý do tại sao Rails ghi đè lên nó) - DanSingerman
Ok tuyệt vời, cảm ơn, điều này là hoàn hảo. :) - Ash


DateTime.now.new_offset(0)

sẽ hoạt động trong Ruby chuẩn (nghĩa là không có ActiveSupport).


157
2018-05-15 00:14



Và đây thực sự là câu trả lời đúng nhất cho câu hỏi. - Ernest
Điều này sẽ có nhiều upvotes hơn. DateTime khác với Thời gian. Tôi cần chính xác điều này. - d11wtq
@ Ash, Nó thực sự là câu trả lời đúng - Abhinay
new_offset đối số phương thức mặc định là 0 rồi. Vì thế DateTime.now.new_offset cũng có thể được sử dụng. - Cryptor


Thật không may, lớp DateTime không có các phương thức tiện lợi có sẵn trong lớp Time để làm điều này. Bạn có thể chuyển đổi bất kỳ đối tượng DateTime nào thành UTC như sau:

d = DateTime.now
d.new_offset(Rational(0, 24))

Bạn có thể chuyển đổi từ UTC sang giờ địa phương bằng cách sử dụng:

d.new_offset(DateTime.now.offset)

Ở đâu d là một đối tượng DateTime trong thời gian UTC. Nếu bạn thích những phương thức này, bạn có thể tạo chúng như sau:

class DateTime
  def localtime
    new_offset(DateTime.now.offset)
  end

  def utc
    new_offset(Rational(0, 24))
  end
end

Bạn có thể thấy điều này trong hành động trong phiên làm việc sau đây:

d = DateTime.now.new_offset(Rational(-4, 24))
 => #<DateTime: 106105391484260677/43200000000,-1/6,2299161> 
1.8.7 :185 > d.to_s
 => "2012-08-03T15:42:48-04:00" 
1.8.7 :186 > d.localtime.to_s
 => "2012-08-03T12:42:48-07:00" 
1.8.7 :187 > d.utc.to_s
 => "2012-08-03T19:42:48+00:00" 

Như bạn có thể thấy ở trên, đối tượng DateTime ban đầu có độ lệch -04: 00 (Giờ Miền Đông). Tôi đang ở Thái Bình Dương Thời gian với một bù đắp -07: 00. Đang gọi localtime như được mô tả trước đây đúng cách chuyển đổi đối tượng DateTime thành giờ địa phương. Đang gọi utc trên đối tượng đúng cách chuyển nó thành giá trị UTC.


8
2017-08-03 20:02





Bạn có thể đặt ENV nếu bạn muốn Time.now và DateTime.now để trả lời trong thời gian UTC.

require 'date'
Time.now #=> 2015-11-30 11:37:14 -0800
DateTime.now.to_s #=> "2015-11-30T11:37:25-08:00"
ENV['TZ'] = 'UTC'
Time.now #=> 2015-11-30 19:37:38 +0000
DateTime.now.to_s #=> "2015-11-30T19:37:36+00:00"

3
2017-11-30 19:40





Hãy thử điều này, làm việc trong Ruby:

DateTime.now.to_time.utc

2
2017-11-11 02:02





Trong irb:

>>d = DateTime.now
=> #<DateTime: 11783702280454271/4800000000,5/12,2299161>
>> "#{d.hour.to_i - d.zone.to_i}:#{d.min}:#{d.sec}"
=> "11:16:41"

sẽ chuyển đổi thời gian thành utc. Nhưng như được đăng nếu nó chỉ là Thời gian bạn có thể sử dụng:

Time.now.utc

và lấy nó ngay lập tức.


1
2018-04-16 11:29





Biểu diễn chuỗi của một DateTime có thể được phân tích bởi lớp Time.

> Time.parse(DateTime.now.to_s).utc
=> 2015-10-06 14:53:51 UTC

1
2017-10-06 14:55