2 November 2007 - 23:04[How to] calculate daylight savings dates with PHP
This Sunday is the “fall back” date for daylight savings, which is awesome. In North America, DST time changes are on the first Sunday of November, and the first Sunday of March. On rare occasions, you might find a need for a PHP function that returns the first Sunday of a November, or the third Friday of January, or the X-th Y-day of Z.
First, let’s make a function to calculate the DST “fall back” date. Some quick planning:
- The function will have a single, optional parameter for the year. (Default will be the current year).
- We’ll loop through the days of the month until we get to the day we want, and return it as a UNIX timestamp.
Begin by defining our function:
function dstFallBack($year = '')
and handle the $year if none is supplied with a ternary operation:
$year = (empty($year)) ? date("Y") : $year ;
loop through the days until we get to the first Sunday (guaranteed to happen within 7 days). A simple for loop will do.
for ($x = 1; $x <= 7; $x++)
get the UNIX timestamp for the day of our iteration (November $x, $year). To do this we use the mktime function.
$date = mktime(0,0,0,11,$x,$year);
Check if the day is a Sunday using the date function. (I used "D" instead of "N" because "D" will work in older versions of PHP.
if (date("D", $date) == 'Sun')
If it's Sunday, then we're done, and we can return the $date
break; // no need to keep looping.
Here's the whole thing:
/*** Gets the date of the DST November "fallback"* In other words, the first Sunday in November** @param int $year* @return int*/function dstFallBack($year = ''){ $year = (empty($year)) ? date("Y") : $year ;
for ($x = 1; $x <= 7; $x++) { $date = mktime(0,0,0,11,$x,$year); if (date("D", $date) == 'Sun') { $sunday = $date; break; } } return $sunday; }
Run it a few times as a test:
echo date("M jS, Y",dstFallBack()) . "\n"; // for 2007: 4-Nov-2007echo date("M jS, Y",dstFallBack(2009)) . "\n"; // 1-Nov-2009echo date("M jS, Y",dstFallBack(2016)) . "\n"; // 6-Nov-2016
The "spring forward" date is on the 2nd Sunday of a month, but the function is only slightly more complicated. Just for fun, we can put together a more reusable function (recall "X-th Y-day of Z").
To do this, just add a sort of flag as we iterate through days, like $Ydays_encountered, and increment it with each iteration.
/** * Get the Xth Y-Day of Month * "Abstract" as a double-entendre... * * @param int $xth * @param int $yday * @param int $month * @param int $year * @return int */function xthYday($xth, $yday, $month, $year = ''){ $year = (empty($year)) ? date("Y") : $year ;
//The Xth Y-day will come up within the first X weeks, //so limit the for loop to X * 7 days. $for_limit = ($xth * 7);
for ($i = 1; $i <= $for_limit; $i++) { $date = mktime(0,0,0,$month,$i,$year); if (date("D", $date) == 'Sun') { $ydays_encountered++; if ($ydays_encountered == $xth) { $xthYday = $date; break; } } } return $xthYday;}
echo date("M jS, Y",xthYday(1,'Sun',11,2007)); // 4-Nov-2007. Seems to work!
Hopefully this will be useful for some kind of events calendar or something.
No Comments | Tags: code, how to