Number of hours between two dates - Ruby - ruby-on-rails

Say I want the difference between tomorrow and now (in hours).
What I've tried:
t = (DateTime.tomorrow - DateTime.now)
(t / 3600).to_i
=> 0
Why does it give 0?
What am I doing wrong?

This is because DateTime.tomorrow does not have any time value. Here:
DateTime.tomorrow
# => Wed, 22 Apr 2015
If you go through official document for DateTime you can see there is no method tomorrow. Its basically Date#tomorrow.
You can use .to_time to get default localtime 00:00:00
DateTime.tomorrow.to_time
# => 2015-04-22 00:00:00 +0530
(DateTime.tomorrow.to_time - DateTime.now) / 1.hours
# => 9.008116581638655
To get exact hour difference between dates:
(DateTime.tomorrow.to_time - Date.today.to_time) / 1.hours
# => 24.0

Try this
t = (DateTime.tomorrow.to_time - Date.today.to_time)
t = (t / 3600).to_i

It returns rational number. You can take days number if you'll use round method:
>> (DateTime.tomorrow - DateTime.now).round
1
Or if you want to take value in hours from now, use Time class:
>> (Date.tomorrow.to_time - Time.now) / 1.hour
11.119436663611111

if you have two dates like
start_time = Time.new(2015,1, 22, 35, 0)
end_time = Time.new(2015,2, 22, 55, 0)
Try Time Difference gem for Ruby at https://rubygems.org/gems/time_difference
def timediff(start, end)
TimeDifference.between(start, end).in_hours
end
and call it like:
timediff(start_time, end_time)
It will work.
Cheers!

There's DateTime#seconds_until_end_of_day:
seconds = DateTime.now.seconds_until_end_of_day
#=> 41133
seconds / 3600
#=> 11
distance_of_time_in_words(seconds)
=> "about 11 hours"

Related

How to get the future nearest time in ruby

Suppose we have current time and then add the 60 munites to the current time.
Time.now + 1.hours
# => 2022-11-01 16:47:02.965861 +0500
after that we get the next half hour like 17:00:00
I'm able to get the previous half hour time from this code, but unable to find the next half hour time.
time = Time.now - 30.minutes
# => 2022-11-01 15:22:59.942013 +0500
Time.at((time.to_time.to_i/1800).round * 1800).to_datetime
# => Tue, 01 Nov 2022 15:00:00 +0500
If I understand you correctly, you want to map:
15:00-15:29 to 17:00
15:30-15:59 to 17:30
You could do so with a conditional and advance and change:
t = Time.current
if t.min < 30
t.advance(hours: 2).change(min: 0)
else
t.advance(hours: 1).change(min: 30)
end
From what I understand you want to round up the time to the next 30 min mark i.e if it is between 5:01 and 5:29 you want to make it 5:30
For that you can just do
time = Time.now + 1.hours
ceil_minutes = 30.minutes
Time.at((time.to_f / ceil_minutes).ceil * ceil_minutes)

Rails get difference between two dates [duplicate]

This question already has answers here:
How to evaluate a date difference in years, months and days (ruby)?
(6 answers)
Closed 8 years ago.
How to get time difference in days,hours,mins
I am trying to do
datetime_A - datetime_B
datetime_A = Sat, 04 Jan 2014 07:00:13 +0000
datetime_B = Fri, 03 Jan 2014 01:09:46 +0000
it returns me something like(35809/28800),bdw what does it means?
I need like 1day,5h,23min
How can do it?
You need to add helper in your rails app to achive this. Ruby not provide any direct way for this. Below is date manipulation using ruby 2.1.0.
2.1.0 :021 > a_date_time = DateTime.now
=> Fri, 26 Dec 2014 16:39:30 +0530 # First Date
2.1.0 :022 > b_date_time = DateTime.now-20
=> Sat, 06 Dec 2014 16:40:03 +0530 # Second Date
2.1.0 :023 > (a_date_time - b_date_time).to_i
=> 19 # Direct date difference
2.1.0 :024 > Seconds = ((a_date_time - b_date_time)*24*60*60).to_i
=> 1727966 # Seconds between two dates
2.1.0 :025 > sec = Seconds % 60
=> 26 # Second diffence to print
2.1.0 :026 > Minutes = Seconds / 60
=> 28799 # Minutes between two dates
2.1.0 :027 > min = Minutes % 60
=> 59 # Minute diffence to print
2.1.0 :028 > Hours = Minutes / 60
=> 479 # Hours between two dates
2.1.0 :029 > hour = Hours % 24
=> 23 #Hour diffence to print
2.1.0 :030 > Days = Hours / 24
=> 19 # Days between two dates
2.1.0 :032 > Days.to_s + 'Days, ' + hour.to_s + 'Hours, '+ min.to_s + 'Mins, ' + sec.to_s + 'Secs'
=> "19Days, 23Hours, 59Mins, 26Secs" # Desired output
An alternative could be to use the ActionView helper distance_of_time_in_words (see the documentation). If normally does not give the exact minor units, but something like "around 5 days".
I like to use the gem time_diff
https://github.com/abhidsm/time_diff
Here is a example how it works
Time.diff(Time.parse('2011-03-06'), Time.parse('2011-03-07'))
# => {:year => 0, :month => 0, :week => 0, :day => 1, :hour => 0, :minute => 0, :second => 0, :diff => '1 day and 00:00:00'}
The value that is being given is a Rational, (http://www.ruby-doc.org/core-2.1.5/Rational.html). It represents the number of days between the two dates. This is actually quite cool, as it can be much more accurate than a float and easily convertible to hours, minutes, seconds etc.

Ruby Time.now and Other dates

I need to get three dates in variables
Today Since Midnight which I have as
t = Time.now.strftime("%Y-%m-%d 00:00:01") # 2012-11-19 00:00:01
Yesterday Since Midnight (i.e. 00:00:00 to 23:59:59)
y1 = 2012-11-18 00:00:01
y2 = 2012-11-19 23:59:59
it is specifically the y1 & y2 variables I need to create as strings for use in a gem. being new to ruby I am a little confused as Time.yesterday doesn't seem to do what I need
EDIT
For this be sure to include
require 'active_support/all'
and ensure the gem is bundled for your application.
Used:
#current = (Time.now).beginning_of_day.utc.strftime("%Y-%m-%d")
#yesterday = (Time.now - 1.day).beginning_of_day.utc.strftime("%Y-%m-%d")
#everything = (Time.now - 2.day).end_of_day.utc.strftime("%Y-%m-%d")
You can do,
t=Time.now
y1=t-1.day
y2=t+1.day
t = Time.now
t - 1.day # => yesterday
t + 1.day # => tomorrow
convert t to date first,
t = t.to_date
t - 1.day # => yesterday
t + 1.day # => tomorrow
Since you are running Rails there's help to get from ActiveSupport
1.day.ago.midnight
Time.new.beginning_of_day
You should also consider not using 2012-11-19 00:00:01 or 2012-11-19 23:59:59.
Instead you could use 00:00:00 and compare with >= or < depending on what you want to achieve. If you always round to seconds then 2012-11-19 00:00:00 to 2012-11-19 23:59:59 would work.

How to add minutes to a Time object

In Ruby, how do I do Time.now + 10.hours?
Is there an equivalent for secs and mins? For example:
Time.now + 15.mins
Ruby (the programming language) doesn't have 10.hours, that's ActiveSupport as part of Ruby on Rails (the web framework). And yes, it does have both minutes and seconds methods.
However, Time#+ (the + method on Time instances) returns a new Time instance that is that many seconds in the future. So without any Ruby on Rails sugar, you can simply do:
irb> t = Time.now
#=> 2011-08-03 22:35:01 -0600
irb> t2 = t + 10 # 10 Seconds
#=> 2011-08-03 22:35:11 -0600
irb> t3 = t + 10*60 # 10 minutes
#=> 2011-08-03 22:45:01 -0600
irb> t4 = t + 10*60*60 # 10 hours
#=> 2011-08-04 08:35:01 -0600
If you are using ActiveSupport, what you are looking for is the full .minutes and .seconds.
Time.now + 10.minutes
Time.now + 10.seconds
Also in ActiveSupport you can do:
10.minutes.from_now
10.minutes.ago
I think you're talking about extensions added by Rails. I think you need 15.minutes.
See the Active Support Core Extensions for Date, DateTime and Time for more information.
Time Object
time = Time.now
Adding minutes to a time object:
time + 5.minutes
There is an advance function in Active Support refer.
You can do the following using advance:
d = DateTime.new(2010, 2, 28, 23, 59, 59)
=> Sun, 28 Feb 2010 23:59:59 +0000
d.advance(hours: 1)
=> Mon, 01 Mar 2010 00:59:59 +0000

Convert Ruby Date to Integer

How can I convert a Ruby Date to an integer?
t = Time.now
# => 2010-12-20 11:20:31 -0700
# Seconds since epoch
t.to_i
#=> 1292869231
require 'date'
d = Date.today
#=> #<Date: 2010-12-20 (4911101/2,0,2299161)>
epoch = Date.new(1970,1,1)
#=> #<Date: 1970-01-01 (4881175/2,0,2299161)>
d - epoch
#=> (14963/1)
# Days since epoch
(d - epoch).to_i
#=> 14963
# Seconds since epoch
d.to_time.to_i
#=> 1292828400
Date cannot directly become an integer. Ex:
$ Date.today
=> #<Date: 2017-12-29 ((2458117j,0s,0n),+0s,2299161j)>
$ Date.today.to_i
=> NoMethodError: undefined method 'to_i' for #<Date: 2017-12-29 ((2458117j,0s,0n),+0s,2299161j)>
Your options are either to turn the Date into a time then an Int which will give you the seconds since epoch:
$ Date.today.to_time.to_i
=> 1514523600
Or come up with some other number you want like days since epoch:
$ Date.today.to_time.to_i / (60 * 60 * 24) ### Number of seconds in a day
=> 17529 ### Number of days since epoch
Time.now.to_i
returns seconds since epoch format
Solution for Ruby 1.8 when you have an arbitrary DateTime object:
1.8.7-p374 :001 > require 'date'
=> true
1.8.7-p374 :002 > DateTime.new(2012, 1, 15).strftime('%s')
=> "1326585600"
I had to do it recently and took some time to figure it out but that is how I came across a solution and it may give you some ideas:
require 'date'
today = Date.today
year = today.year
month = today.mon
day = day.mday
year = year.to_s
month = month.to_s
day = day.to_s
if month.length <2
month = "0" + month
end
if day.length <2
day = "0" + day
end
today = year + month + day
today = today.to_i
puts today
At the date of this post, It will put 20191205.
In case the month or day is less than 2 digits it will add a 0 on the left.
I did like this because I had to compare the current date whit some data that came from a DB in this format and as an integer. I hope it helps you.

Resources