# Time Calculations And Time Between certain times

**URL:** <https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867>\
**Category:** Rails\
**Created:** [October 12, 2006, 1:10am UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867 "2006-10-12T01:10:41Z")\
**Posts on this page:** 9\
**Page:** 1

<div class="post-metadata">

**Author:** ![sw0rdfish](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/edb3f5/32.png) [@sw0rdfish](https://www.ruby-forum.com/u/sw0rdfish)\
**Post date:** [October 12, 2006, 1:10am UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867/1 "2006-10-12T01:10:41Z")

</div>

Ok I’ve wasted all day, and I’m hoping it’s because I’m a noob, and  
that it can be done…

Say I’ve got two random times, they’re stored in the database as time  
objects so if in the database I have 4:15:00 to rails they come out as  
January 1st 2000 4:15:00 for example…

No I have two of these, and I need to check how much of them is between  
11PM on January 1st and 6AM on January second…

I tried to create time objects to hold 11PM January 1st and so on, but  
I was unable to figure it out.

What I’m trying to do is figure out how many hours someone worked  
between those times, to I can pay them extra. Any advice would be very  
much appreciated.

Thanks

---

<div class="post-metadata">

**Author:** ![sw0rdfish](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/edb3f5/32.png) [@sw0rdfish](https://www.ruby-forum.com/u/sw0rdfish)\
**Post date:** [October 12, 2006, 2:19am UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867/2 "2006-10-12T02:19:18Z")

</div>

Try something like this:

start\_hour = 17 # start work at 5pm (24 hour time)  
end\_hour = 3 # finish work at 3am

# default to no overtime

overtime\_hours = 0

# worked the whole overtime shift?

overtime\_hours = 7 if start\_hour\<=23 && end\_hour\>=6

# start at/before 11 and finished after midnight but before whole shift

overtime\_hours = 1+end\_hour if start\_hour\<=23 && end\_hour\<6

# start at/before 11 and finished before midnight

overtime\_hours = end\_hour-23 if start\_hour\<=23 && end\_hour\>=23

# start between 11 and 12 and finished after 6

overtime\_hours = 6+ if start\_hour\>=23 && end\_hour\>=6  
…etc…

on second thoughts… thats pretty ‘kludgey’. But you get the idea.

---

<div class="post-metadata">

**Author:** ![sw0rdfish](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/edb3f5/32.png) [@sw0rdfish](https://www.ruby-forum.com/u/sw0rdfish)\
**Post date:** [October 12, 2006, 2:23am UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867/3 "2006-10-12T02:23:19Z")

</div>

Scratch my last reply, this is much better:

@start\_hour = 22 # start at 10pm 24hour time  
@end\_hour = 3.5 # end at 3:30am - notice the .5 means 30 minutes

@start\_overtime=23 #overtime starts at 11pm  
@end\_overtime=6 #overtime finishes at 6am

def maximum(a,b)  
a\>b ? a : b  
end

def find\_overtime

# firstly, find when they started and finished, relative to the start

of overtime  
s = @start\_hour - @start\_overtime #start work  
e = @end\_hour - @start\_overtime #end work  
e += 24 if @end\_hour\<@start\_hour # if they worked past midnight

# this is the important line

overtime = maximum(e,0) - maximum(s,0)  
end

print find\_overtime

---

<div class="post-metadata">

**Author:** ![sw0rdfish](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/edb3f5/32.png) [@sw0rdfish](https://www.ruby-forum.com/u/sw0rdfish)\
**Post date:** [October 12, 2006, 3:17am UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867/4 "2006-10-12T03:17:39Z")

</div>

This looks good Chirs,

Thanks… right after the hockey game I’ll give it a shot!

Thanks again!

---

<div class="post-metadata">

**Author:** ![sw0rdfish](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/edb3f5/32.png) [@sw0rdfish](https://www.ruby-forum.com/u/sw0rdfish)\
**Post date:** [October 12, 2006, 5:52am UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867/5 "2006-10-12T05:52:07Z")

</div>

I always convert to epoch and do the math that way… dunno… not  
saying it’s what you’re needing but would work.

---

<div class="post-metadata">

**Author:** ![sw0rdfish](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/edb3f5/32.png) [@sw0rdfish](https://www.ruby-forum.com/u/sw0rdfish)\
**Post date:** [October 12, 2006, 4:21pm UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867/6 "2006-10-12T16:21:10Z")

</div>

Yeah that gives me the difference, but I need to know how much time was  
spent between two specific time periods. Subtracting gives me total  
time worked, but I need to know how much of that time, was between 11PM  
and 6AM.

---

<div class="post-metadata">

**Author:** ![sw0rdfish](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/edb3f5/32.png) [@sw0rdfish](https://www.ruby-forum.com/u/sw0rdfish)\
**Post date:** [October 12, 2006, 3:53am UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867/7 "2006-10-12T03:53:54Z")

</div>

Hi,

Cant you just get the difference from the times like this?  
@start, @end are DateTime

@diff = @end - @start # this will return the diff in seconds have to  
divide by 3600 to get it in hours.

Hope it works for u.

D.

---

<div class="post-metadata">

**Author:** ![sw0rdfish](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/edb3f5/32.png) [@sw0rdfish](https://www.ruby-forum.com/u/sw0rdfish)\
**Post date:** [October 18, 2006, 10:38am UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867/8 "2006-10-18T10:38:53Z")

</div>

Ok,  
Lets see if this works…

@start = (@start.hour \> 23) ? @start : @start.change(:hours=\>23)  
@end = (@end.hour \< 6) ? @end : @end.change(:hour=\>6)  
@overtime = @end - @start #again in ms

This works if the days are consecutive…

---

<div class="post-metadata">

**Author:** ![sw0rdfish](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/edb3f5/32.png) [@sw0rdfish](https://www.ruby-forum.com/u/sw0rdfish)\
**Post date:** [October 18, 2006, 10:39am UTC](https://www.ruby-forum.com/t/time-calculations-and-time-between-certain-times/71867/9 "2006-10-18T10:39:21Z")

</div>

ok… for the sake of archival needs and in case anyone else tries to  
do this… here’s what my final solution was…

this is in the model for the class that holds the “day of work” so to  
speak…

#if the start time is greater than the end time, move end time to Jan  
2nd

if self.finish\_time \< self.call\_time  
#add 86, 400 seconds  
self.finish\_time += ( 60 \* 60 \* 24 )  
end

# calculate the total time in seconds, convert to hours… and round to

the next full interger( .ceil ) ( 2.01 becomes 3 because they are paid  
for every hour or part thereof )

hours\_worked = ( ( self.finish\_time - self.call\_time ) / 3600 ).ceil

#-create constants to hold the point in time where 6AM and 11PM are on  
Jan1st and 2nd  
jan\_one\_eleven\_pm\_epoch = 946785600  
jan\_one\_six\_am\_epoch = 946724400  
jan\_two\_six\_am\_epoch = 946810800

##- night premiums  
#- check to see if clal time or end time falls between OT period ( need  
to do more to check if the employee works 10Pm to 7AM for example…  
but that’s easy )  
if( self.call\_time.to\_i \>= jan\_one\_eleven\_pm\_epoch ||  
self.call\_time.to\_i \<= jan\_one\_six\_am\_epoch ||  
( self.finish\_time.to\_i \<= jan\_two\_six\_am\_epoch &&  
self.finish\_time.to\_i \>= jan\_one\_eleven\_pm\_epoch ) )

## #- use the call\_time or use 11PM, use finish or use 6AM etc… convert to Float and convert to hours night\_hours = ( minimum( self.finish\_time.to\_i, jan\_two\_six\_am\_epoch )

```
                   maximum( self.call_time.to_i,

```

jan\_one\_eleven\_pm\_epoch ) ).to\_f / 3600

##private methods from Chirs…  
private

def maximum(a,b)  
a\>b ? a : b  
end

def minimum(a,b)  
a\<b ? a : b  
end

Works like a charm!
