Take the 2-minute tour ×

Ok so I am working on a calendar application within my CRM system and I need to find the upper and lower bounds of the half an hour surrorunding the timestamp at which somebody entered an event in the calendar in order to run some SQL on the DB to determine if they already have something booked in within that timeslot.

For example I have the timestamp of 1330518155 = 29 February 2012 16:22:35 GMT+4 so I need to get 1330516800 and 1330518600 which equal 16:00 and 16:30.

If anyone has any ideas or think I am approaching developing the calendar in a stupid way let me know! Its my first time on such a task involving so much work with times and dates so any advice appreciated!

share|improve this question
try to use the function in manual - php.net/manual/en/function.strtotime.php - should be helpful, you can add or remove any amount of time from timestamp very easy. –  Kamil Mar 9 '12 at 19:13
what does this have to do with times and dates? it's simple math –  miki Mar 9 '12 at 19:14
add comment

7 Answers

up vote 23 down vote accepted

Use modulo.

$prev = 1330518155 - (1330518155 % 1800);
$next = $prev + 1800;

The modulo operator gives the remainder part of division.

share|improve this answer
That will find seconds since the hour, but that's only part of the problem, because if the minutes are >= 30, the time bracket is H:30 to H+1:00 –  dj_segfault Mar 9 '12 at 20:31
Since we're dividing by 1800, it will give seconds since the last half hour increment (1:00, 1:30, 2:00, 2:30, etc...). If it's 1:30:01, the modulo operation will return 1 and $prev will be 1:30. Adding 1800 seconds will make $next equal to 2:00. Similarly, if it's 1:29:59, the modulo will be 1799 and $prev will be 1:00. Again, adding 1800 will make $next 1:30. –  SenorAmor Mar 9 '12 at 20:56
So simple sometimes you just try to over think things and look for a function to do some basic arithmetic! –  Ash Mar 10 '12 at 11:44
I really like how elegant this is. Not only is it done with only arithmetic, it will also work regardless of time zone (except in the Chatham Islands and Nepal, which are the only two time zones off by 15 minutes instead of 30). –  Jazz Aug 24 '12 at 17:55
Modulneto! hahahahaha –  Adam F Sep 3 '13 at 17:09
add comment

As you probably know, a UNIX timestamp is a number of seconds, so substract/add 1800 (number of seconds in 30 minutes) and you will get the desired result.

share|improve this answer
that's not really rounding though, is it? –  thescientist Mar 9 '12 at 19:15
That will find 30 minutes before and 30 minutes after, not the "on the hour" and "on the half hour" bounding the time. Please look at his example again. –  dj_segfault Mar 9 '12 at 19:32
add comment

You could use the modulo operator.

$time -= $time % 3600; // nearest hour (always rounds down)

Hopefully this is enough to point you in the right direction, if not please add a comment and I'll try to craft a more specific example.

share|improve this answer
add comment

I'd use the localtime and the mktime function.

$localtime = localtime($time, true);
$localtime['tm_sec'] = 0;
$localtime['tm_min'] = 30;
$time = mktime($localtime);
share|improve this answer
add comment

PHP does have a DateTime class and a whole slough of methods that it provides. You could use these if you like, but I find it easier to use the built-in date() and strtotime() functions.

Here's my solution:

// Assume $timestamp has the original timestamp, i.e. 2012-03-09 16:23:41

$day = date( 'Y-m-d', $timestamp ); // $day is now "2012-03-09"
$hour = (int)date( 'H', $timestamp ); // $hour is now (int)16
$minute = (int)date( 'i', $timestamp ); // $minute is now (int)23

if( $minute < 30 ){
  $windowStart = strtotime( "$day $hour:00:00" );
  $windowEnd   = strtotime( "$day $hour:30:00" );
} else {
  $windowStart = strtotime( "$day $hour:30:00" );
  if( ++$hour > 23 ){
    // if we crossed midnight, fix the date and set the hour to 00
    $day = date( 'Y-m-d', $timestamp + (24*60*60) );
    $hour = '00';
  $windowEnd   = strtotime( "$day $hour:00:00" );

// Now $windowStart and $windowEnd are the unix timestamps of your endpoints

There are a few improvements that can be made on this, but that's the basic core.

[Edit: corrected my variable names!]

[Edit: I've revisited this answer because, to my embarrassment, I realized that it didn't handle the last half-hour of a day correctly. I've fixed that issue. Note that $day is fixed by adding a day's worth of seconds to the timestamp -- doing it this way means we don't have to worry about crossing month boundaries, leap days, etc. because PHP will format it correctly for us regardless.]

share|improve this answer
add comment

This could be simplified a little, but shows the complete thought process. Uses some of SenorAmor's code. Props.

$time = 1330518155 ;
$offset = ($time % 1800);
$prev = $time - $offset;
if($offset > 900){
  $newtime = $prev + 1800;
  $newtime = $prev
share|improve this answer
add comment

If you need to get the current time and then apply the rounding (down) of the time, I would do the following:

$now = date('U');
$offset = ($now % 1800);
$now = $now-$offset;
    echo date('g:i',$now);
    $now += 1800;

Or you could round up by adding the offset, and do something more than just echo the time. The for loop then displays the 12 hours of increments. I used the above in a recent project.

share|improve this answer
add comment

Your Answer


