I want to calculate the difference between 2 times. start_time: 22:00 (Rails interprets this as 2015-12-31 22:00:00 +0100) second_time: 02:00 (Rails interprets this as 2015-12-31 02:00:00 +0100). The second time is 4 hours later, so in the next day. Is there a way to calculate this difference?
我想计算2次之间的差异。 start_time:22:00(Rails将其解释为2015-12-31 22:00:00 +0100)second_time:02:00(Rails将此解释为2015-12-31 02:00:00 +0100)。第二次是4小时后,所以在第二天。有没有办法计算这种差异?
I can not simply do this: second_time - first_time, because this gives me a difference of 22 hours instead of 4 hours.
我不能简单地这样做:second_time - first_time,因为这给了我22小时而不是4小时的差异。
Edit: Some background information: A job is starting at 22:00 and ending the next day at 02:00. Because i fill in the form of this job only times, this times for the above 2 values are 2015-12-31 22:00:00 +0100 and 2015-12-31 02:00:00 +0100. I don't want the user to fill in the time including the date. The real difference between the times should be 4 hours.
编辑:一些背景信息:作业从22:00开始,到第二天02:00结束。因为我只填写这份工作的形式,所以上述2个值的时间是2015-12-31 22:00:00 +0100和2015-12-31 02:00:00 +0100。我不希望用户填写包括日期在内的时间。时间之间的真正差异应该是4个小时。
So what i actually want is calculate the difference between 22:00 and 02:00 (in the next day).
所以我真正想要的是计算22:00和02:00(第二天)之间的差异。
3 个解决方案
#1
8
I don't understand why you think it should return 4 hours or why it does return 22 hours. 20 hours would be correct for your example:
我不明白为什么你认为它应该返回4小时或为什么它会返回22小时。你的例子20小时是正确的:
require 'time'
a = Time.parse('2015-12-31 22:00:00 +0100')
b = Time.parse('2015-12-31 02:00:00 +0100')
a - b
#=> 72000.0 # difference in seconds
(a - b) / 3600
#=> 20.0 # difference in hours
Update: It seems like you are dealing only with the time portion and not with the actual date. And I assume the maximum difference you will have to deal with is 24 hours:
更新:您似乎只处理时间部分而不是实际日期。我假设您必须处理的最大差异是24小时:
def time_difference(time_a, time_b)
difference = time_b - time_a
if difference > 0
difference
else
24 * 3600 + difference
end
end
a = Time.parse('2015-12-31 22:00:00 +0100')
b = Time.parse('2015-12-31 02:00:00 +0100')
time_difference(a, b) / 3600
# => 4 # hours
a = Time.parse('2015-12-31 02:00:00 +0100')
b = Time.parse('2015-12-31 22:00:00 +0100')
time_difference(a, b) / 3600
# => 20 # hours
#2
1
I'd write it thusly (before adding data checks), in an attempt to make it self-documenting:
我这样写(在添加数据检查之前),试图让它自我记录:
require 'time'
DT_FMT = '%Y-%m-%d %H:%M:%S %z'
SECONDS_PER_DAY = 24*60*60
def hours_elapsed(start_str, finish_str)
start = DateTime.strptime(start_str, DT_FMT).to_time
finish = DateTime.strptime(finish_str, DT_FMT).to_time
finish = same_time_tomorrow(finish) if finish < start
(finish-start)/3600
end
def same_time_tomorrow(time)
time + SECONDS_PER_DAY
end
hours_elapsed '2015-12-31 22:00:00 +0100', '2015-12-31 02:00:00 +0100'
#=> 4.0
hours_elapsed '2015-12-31 02:00:00 +0100', '2015-12-31 22:00:00 +0100'
#=> 20.0
#3
0
Old question but I did a nice method to deal with it:
老问题,但我做了一个很好的方法来处理它:
def time(start,ending)
if start != ending
medidas=["year","month","day","hour","minute","second"]
array=[1970,1,1,0,0,0]
text = ""
Time.at(ending-start).utc.to_a.take(6).reverse.each_with_index do |k,i|
text = "#{text} #{I18n.translate medidas[i].to_sym, count: k-array[i]}"
end
text = text.strip.squish
pos = text.rindex(" ",(text.rindex(" ")-1))
unless pos.nil?
text = text.insert(pos," and")
end
text = text.strip.squish #This shouldn't be needed but just in case
else
"0 seconds"
end
end
Then in config/locales/en.yml I added:
然后在config / locales / en.yml中我添加了:
en:
año:
zero: ''
one: '1 year'
other: '%{count} years'
mes:
zero: ''
one: '1 month'
other: '%{count} months'
dia:
zero: ''
one: '1 day'
other: '%{count} days'
hora:
zero: ''
one: '1 hour'
other: '%{count} hours'
minuto:
zero: ''
one: '1 minute'
other: '%{count} minutes'
segundo:
zero: ''
one: '1 second'
other: '%{count} seconds'
So for example when you call:
例如,当您致电时:
start = Time.now
ending = start + (60*60)
time(start,ending)
=> "1 hour"
ending = start + (60*60*28)
time(start,ending)
=> "1 day and 4 hours"
ending = start + (53*60*5874)
time(start,ending)
=> "7 months 4 days 4 hours and 42 minutes"
Hope it's useful
希望它有用
#1
8
I don't understand why you think it should return 4 hours or why it does return 22 hours. 20 hours would be correct for your example:
我不明白为什么你认为它应该返回4小时或为什么它会返回22小时。你的例子20小时是正确的:
require 'time'
a = Time.parse('2015-12-31 22:00:00 +0100')
b = Time.parse('2015-12-31 02:00:00 +0100')
a - b
#=> 72000.0 # difference in seconds
(a - b) / 3600
#=> 20.0 # difference in hours
Update: It seems like you are dealing only with the time portion and not with the actual date. And I assume the maximum difference you will have to deal with is 24 hours:
更新:您似乎只处理时间部分而不是实际日期。我假设您必须处理的最大差异是24小时:
def time_difference(time_a, time_b)
difference = time_b - time_a
if difference > 0
difference
else
24 * 3600 + difference
end
end
a = Time.parse('2015-12-31 22:00:00 +0100')
b = Time.parse('2015-12-31 02:00:00 +0100')
time_difference(a, b) / 3600
# => 4 # hours
a = Time.parse('2015-12-31 02:00:00 +0100')
b = Time.parse('2015-12-31 22:00:00 +0100')
time_difference(a, b) / 3600
# => 20 # hours
#2
1
I'd write it thusly (before adding data checks), in an attempt to make it self-documenting:
我这样写(在添加数据检查之前),试图让它自我记录:
require 'time'
DT_FMT = '%Y-%m-%d %H:%M:%S %z'
SECONDS_PER_DAY = 24*60*60
def hours_elapsed(start_str, finish_str)
start = DateTime.strptime(start_str, DT_FMT).to_time
finish = DateTime.strptime(finish_str, DT_FMT).to_time
finish = same_time_tomorrow(finish) if finish < start
(finish-start)/3600
end
def same_time_tomorrow(time)
time + SECONDS_PER_DAY
end
hours_elapsed '2015-12-31 22:00:00 +0100', '2015-12-31 02:00:00 +0100'
#=> 4.0
hours_elapsed '2015-12-31 02:00:00 +0100', '2015-12-31 22:00:00 +0100'
#=> 20.0
#3
0
Old question but I did a nice method to deal with it:
老问题,但我做了一个很好的方法来处理它:
def time(start,ending)
if start != ending
medidas=["year","month","day","hour","minute","second"]
array=[1970,1,1,0,0,0]
text = ""
Time.at(ending-start).utc.to_a.take(6).reverse.each_with_index do |k,i|
text = "#{text} #{I18n.translate medidas[i].to_sym, count: k-array[i]}"
end
text = text.strip.squish
pos = text.rindex(" ",(text.rindex(" ")-1))
unless pos.nil?
text = text.insert(pos," and")
end
text = text.strip.squish #This shouldn't be needed but just in case
else
"0 seconds"
end
end
Then in config/locales/en.yml I added:
然后在config / locales / en.yml中我添加了:
en:
año:
zero: ''
one: '1 year'
other: '%{count} years'
mes:
zero: ''
one: '1 month'
other: '%{count} months'
dia:
zero: ''
one: '1 day'
other: '%{count} days'
hora:
zero: ''
one: '1 hour'
other: '%{count} hours'
minuto:
zero: ''
one: '1 minute'
other: '%{count} minutes'
segundo:
zero: ''
one: '1 second'
other: '%{count} seconds'
So for example when you call:
例如,当您致电时:
start = Time.now
ending = start + (60*60)
time(start,ending)
=> "1 hour"
ending = start + (60*60*28)
time(start,ending)
=> "1 day and 4 hours"
ending = start + (53*60*5874)
time(start,ending)
=> "7 months 4 days 4 hours and 42 minutes"
Hope it's useful
希望它有用