It may be useful to note that no E_WARNINGS or E_NOTICES are give if you specify a date <1901 or >2038 on systems where time_t is a 32bit signed integer.
If a date is specified outside of the allowed range you may get some unexpected results as no timestamp will be returned.
mktime
(PHP 4, PHP 5)
mktime — Gibt den Unix-Timestamp/Zeitstempel für ein Datum zurück
Beschreibung
$hour = date("H")
[, int $minute = date("i")
[, int $second = date("s")
[, int $month = date("n")
[, int $day = date("j")
[, int $year = date("Y")
[, int $is_dst = -1
]]]]]]] )Gibt den Unix-Timestamp entsprechend der gegebenen Argumente zurück. Dieser Timestamp ist ein Long Integer, der die Anzahl der Sekunden zwischen der Unix-Epoche (01. Januar 1970 00:00:00 GMT) und dem angegebenen Zeitpunkt enthält.
Einzelne Argumente können von rechts nach links weggelassen werden. Sie werden dann mit den Werten der lokalen Systemzeit bzw. des lokalen Systemdatums ersetzt.
Anmerkungen
Hinweis:
Seit PHP 5.1 wirft mktime() eine
E_STRICT-Notice, wenn die Funktion ohne Argumente aufgerufen wird. Verwenden Sie in diesem Fall stattdessen die time()-Funktion.
Parameter-Liste
-
hour -
Die Stunde.
-
minute -
Die Minute.
-
second -
Die Anzahl der Sekunden nach der Minute.
-
month -
Der Monat.
-
day -
Der Tag.
-
year -
Die Jahreszahl, die zwei- oder vierstellig angegeben werden kann. Werte von 0 bis 69 werden auf 2000-2069 gemappt, Werte von 70 bis 100 auf 1970-2000. Auf Systemen, auf denen time_t ein 32-Bit Signed Integer ist (das sind die meisten der heutigen Systeme), beginnt der gültige Wertebereich für
yearbei 1901 und endet bei 2038. Allerdings begrenzen PHP-Versionen vor 5.1.0 den Bereich auf einigen Systemen (z.B. Windows) auf 1970-2038. -
is_dst -
is_dstkann bei Sommerzeit (DST) auf 1 gesetzt werden, der Wert 0 steht für Winter-/Normalzeit und -1 (Standardwert) heißt, dass unbekannt ist, ob gerade Sommer- oder Winterzeit herrscht. Sofern unbekannt, versucht PHP, dies selbst herauszufinden. Das kann zu unerwarteten (aber dennoch korrekten) Ergebnissen führen. Einige Zeitangaben sind ungültig, wenn die automatische Zeitumstellung auf dem System aktiviert ist, auf dem PHP läuft, oder auf dem der Parameteris_dstden Wert 1 hat. Wenn die Sommerzeit (DST) z.B. um 02:00 Uhr aktiviert wird, sind alle Zeitangaben zwischen 02:00 Uhr und 03:00 Uhr ungültig und mktime() gibt einen undefinierten (meist negativen) Wert zurück. Einige Betriebssyteme (z.B. Solaris 8) nehmen die Zeitumstellung um Mitternacht vor, so dass die Zeitangabe 0:30 als 23:30 des vorherigen Tages interpretiert wird.Hinweis:
Seit PHP 5.1.0 gilt dieses Parameter als veraltet und wird nicht mehr zur Verwendung empfohlen. Verwenden Sie daher die neuen Features zum Handling von Zeitzonen.
Rückgabewerte
mktime() gibt den zu den übergebenen Argumenten
passenden Unix-Timestamp zurück. Wenn die Argumente ungültig sind, gibt
die Funktion FALSE zurück (vor PHP 5.1 wurde dann -1
zurückgegeben).
Fehler/Exceptions
Jeder Aufruf der Datums- und Zeitfunktionen
generiert eine E_NOTICE-Warnung,
wenn die Zeitzone ungültig ist und eine E_STRICT-Nachricht
oder eine E_WARNING-Warnung,
wenn die Systemeinstellung oder die TZ-Umgebungsvariable
genutzt wird. Siehe auch date_default_timezone_set()
Changelog
| Version | Beschreibung |
|---|---|
| 5.3.0 |
mktime() wirft nun eine
E_DEPRECATED-Notice, wenn der
is_dst verwendet wird.
|
| 5.1.0 |
Der Parameter is_dst wurde als veraltet
markiert.
Die Funktion gibt nun im Fehlerfall statt -1
FALSE zurück.
Die Funktion wurde dahingehend gefixt, dass sie für Jahr, Monat und
Tag auch den Wert 0 entgegennimmt.
|
| 5.1.0 |
Wenn ohne Argumente aufgerufen, wirft mktime()
eine E_STRICT-Notice. Verwenden Sie stattdessen
die Funktion time().
|
| 5.1.0 |
Erzeugt nun |
Beispiele
Beispiel #1 Einfaches mktime()-Beispiel
<?php
// Setzt die zu verwendende Standardzeitzone. Verfügbar seit PHP 5.1
date_default_timezone_set('UTC');
// Gibt aus: July 1, 2000 is on a Saturday
echo "July 1, 2000 is on a " . date("l", mktime(0, 0, 0, 7, 1, 2000));
// Gibt etwas aus wie: 2006-04-05T01:02:03+00:00
echo date('c', mktime(1, 2, 3, 4, 5, 2006));
?>
Beispiel #2 mktime()-Beispiel
mktime() ist hilfreich bei Datumsberechnungen und -prüfungen, da automatisch das korrekte Datum für Werte außerhalb der gültigen Bereiche berechnet wird. So wird in den folgenden Beispielen immer die Zeichenkette "Jan-01-1998" ausgegeben.
<?php
echo date("M-d-Y", mktime(0, 0, 0, 12, 32, 1997));
echo date("M-d-Y", mktime(0, 0, 0, 13, 1, 1997));
echo date("M-d-Y", mktime(0, 0, 0, 1, 1, 1998));
echo date("M-d-Y", mktime(0, 0, 0, 1, 1, 98));
?>
Beispiel #3 Letzter Tag des nächsten Monats
Der letzte Tag eines gegebenen Monats kann als Tag "0" des folgenden Monats ausgedrückt werden, nicht jedoch als Tag "-1". Beide folgenden Beispiele ergeben die Zeichenkette "Letzter Tag im Februar 2000 ist der 29."
<?php
$letzterTag = mktime(0, 0, 0, 3, 0, 2000);
echo strftime("Letzter Tag im Februar 2000 ist der %d.", $letzterTag);
$letzterTag = mktime(0, 0, 0, 4, -31, 2000);
echo strftime("Letzter Tag im Februar 2000 ist der %d.", $letzterTag);
?>
Anmerkungen
Vor PHP 5.1.0 wurden negative Timestamps von keiner bekannten Windowsversion oder anderen Betriebssystemen unterstützt. Daher war der Bereich gültiger Jahresangaben auf Werte zwischen 1970 und 2038 beschränkt.
Siehe auch
- gmmktime() - Gibt einen Unix-Timestamp (Zeitstempel) für ein GMT Datum zurück
- date() - Formatiert ein(e) angegebene(s) Ortszeit/Datum
- time() - Gibt den aktuellen Unix-Timestamp/Zeitstempel zurück
mktime
11-Jul-2007 03:04
02-May-2007 12:24
<?php
//the date of the variable holding the original date value
$date = "2007-04-30";
//format the date for mktime() function -- you need day, month, year
$year = substr($date, 0,4);
$month = substr($date, 5, 2);
$day = substr($date, 8, 2);
//check the results
echo $year;
echo "<br>";
echo $month;
echo "<br>";
echo $day;
//the variable to hold the new date plus 14 days
$new_date = date("Y-m-d", mktime(0, 0, 0, $month, $day +14, $year));
//check the results of new date
echo "<br>";
echo $new_date;
?>
08-Apr-2007 11:29
Simple date compare:
mktime(0, 0, 0) >= mktime(0, 0, 0, $_POST['MonthVld'], $_POST['DayVld'], $_POST['YrVld'])
mktime(0, 0, 0) creates a unix time of the current date.
mktime(0, 0, 0, $_POST['MonthVld'], $_POST['DayVld'], $_POST['YrVld']) creates a unix time of the date that your user enters.
31-Mar-2007 06:46
You cannot simply subtract or add month VARs using mktime to obtain previous or next months as suggested in previous user comments (at least not with a DD > 28 anyway).
If the date is 03-31-2007, the following yeilds March as a previous month. Not what you wanted.
<?php
$dateMinusOneMonth = mktime(0, 0, 0, (3-1), 31, 2007 );
$lastmonth = date("n | F", $dateMinusOneMonth);
echo $lastmonth; //---> 3 | March
?>
mktime correctly gives you back the 3rd of March if you subtract 1 month from March 31 (there are only 28 days in Feb 07).
If you are just looking to do month and year arithmetic using mktime, you can use general days like 1 or 28 to do stuff like this:
<?php
$d_daysinmonth = date('t', mktime(0,0,0,$myMonth,1,$myYear)); // how many days in month
$d_year = date('Y', mktime(0,0,0,$myMonth,1,$myYear)); // year
$d_isleapyear = date('L', mktime(0,0,0,$myMonth,1,$myYear)); // is YYYY a leapyear?
$d_firstdow = date('w', mktime(0,0,0,$myMonth,'1',$myYear)); // FIRST falls on what day of week (0-6)
$d_firstname = date('l', mktime(0,0,0,$myMonth,'1',$myYear)); // FIRST falls on what day of week Full Name
$d_month = date('n', mktime(0,0,0,$myMonth,28,$myYear)); // month of year (1-12)
$d_monthname = date('F', mktime(0,0,0,$myMonth,28,$myYear)); // Month Long name (July)
$d_month_previous = date('n', mktime(0,0,0,($myMonth-1),28,$myYear)); // PREVIOUS month of year (1-12)
$d_monthname_previous = date('F', mktime(0,0,0,($myMonth-1),28,$myYear)); // PREVIOUS Month Long name (July)
$d_month_next = date('n', mktime(0,0,0,($myMonth+1),28,$myYear)); // NEXT month of year (1-12)
$d_monthname_next = date('F', mktime(0,0,0,($myMonth+1),28,$myYear)); // NEXT Month Long name (July)
$d_year_previous = date('Y', mktime(0,0,0,$myMonth,28,($myYear-1))); // PREVIOUS year
$d_year_next = date('Y', mktime(0,0,0,$myMonth,28,($myYear+1))); // NEXT year
$d_weeksleft = (52 - $d_weekofyear); // how many weeks left in year
$d_daysinyear = $d_isleapyear ? 366 : 365; // set correct days in year for leap years
$d_daysleft = ($d_daysinyear - $d_dayofyear); // how many days left in year
?>
30-Mar-2007 10:16
a conversion from the ISO date format 'yyyy-mm-dd' can simply be done by
<?php
$timestamp = strtotime('2007-03-29');
$timestamp = strtotime('2007-03-29 11:27:33');
?>
14-Mar-2007 05:14
A more complete MySQL to Unix timestamp function:
function mysql_to_ts($mysql_time) {
if (!preg_match('/^(\\d{4})-(\\d{2})-(\\d{2}) (\\d{2}):(\\d{2}):(\\d{2})$/', $mysql_time, $matches)) {
return NULL;
}
return mktime($matches[4], $matches[5], $matches[6], $matches[2], $matches[3], $matches[1]);
}
11-Mar-2007 10:31
This function returns no negative results inside of XEN guests.
24-Feb-2007 08:17
Here's a handy function which will convert dates in MySQL format (yyyy-mm-dd) to a Unix timestamp. While this can also be done within MySQL queries via the UNIX_TIMESTAMP() function, it is not always convenient to do so.
// Returns the Unix timestamp of a MySQL date (YYYY-MM-DD)
function mysqldate_to_unix_timestamp($date) {
list($year, $month, $day) = explode('-', $date);
return mktime(0, 0, 0, $month, $day, $year);
}
29-Jan-2007 07:35
To Stephen:
You left out one other important difference between human time and timestamps, leap seconds, these get added and removed as needed up to twice a year depending on the earths rotational speed (if the earth spins faster or slower over a period of time).
08-Jan-2007 11:43
There are several warnings here about using mktime() to determine a date difference because of daylight savings time. However, nobody seems to have mentioned the other obvious problem, which is leap years.
Leap years mean that any effort to use mktime() and time() to determine the age (positive or negative) of some timestamp in years will be flawed. There are some years that are 366 days long, therefore you cannot say that there is a set number of seconds per year.
Timestamps are good for determining *real* time, which is not the same thing as *human calendar* time. The Gregorian calendar is only an approximation of real time, which is tweaked with daylight savings time and leap years to make it conform more to humans' expectations of how time should or ought to work. Timestamps are not tweaked and therefore are the only authoritative way of recording in computers a proper order of succession of events, but they cannot be integrated with a Gregorian system unless you take both leap years and DST into account. Otherwise, you may get the wrong number of years when you are approaching a value of exactly X years.
As for PHP, you could still use timestamps as a way of determining age if you took into account not only DST but also whether or not each year is a leap year and adjusted your calculations accordingly. However, this could become messy and inefficient.
There is an alternative approach to calculating days given the day, month and year of the dates to be compared. Compare the years first, and then compare the month and day - if the month and day have already passed (or, if you like, if they match the current month and day), then add 1 to the total for the years.
This solution works because it stays within the Gregorian system and doesn't venture into the world of timestamps.
Here is a good discussion of this issue:
http://forums.devshed.com/php-development-5/
need-to-get-the-age-between-dob-
and-today-29925.html?&highlight=age+leap
[the above link was too long; combine the three lines to get the URL]
There is also the issue of leap seconds, but this will only arise if you literally need to get the *exact* age in seconds. In that case, of course, you would also need to verify that your timestamps are exactly correct and are not delayed by script processing time, plus you would need to determine whether your system conforms to UTC, etc. I expect this will hardly be an issue for anybody using PHP, however if you are interested there is an article on this issue on Wikipedia:
http://en.wikipedia.org/wiki/Leap_second
07-Nov-2006 01:42
There are several notes for mktime which use the number 86400 to differentiate two days. However this technique may pose a problem in case there is a day where the hour change between the two dates to compare.
Consequently, if you want the timestamp difference between the day where the hour change and the next day, it will not be equals to 86400 but either 82800 in case its the winter change of hour day or 90000 for the summer change of hour day.
For example in 2006 :
<?php
echo mktime(0,0,0,10,29,2006) - mktime(0,0,0,10,30,2006); // -90 000
?>
31-Oct-2006 10:28
As I see it, this function should default to zero for the first 3 arguments but one for the next two.
It makes sense to talk about the 0th hour of the day (midnight) or the 0th minute of the hour or the 0th second of the minute, but it makes no sense to talk about the 0th day of the month or the 0th month of the year.
The example of why this change should happen is below:
<select id="month" name="month">
<?php
for ($i = 1; $i <= 12; $i++)
echo '<option value="'.$i.'">'.date('F',mktime(0,0,0,$i)).'</option>';
?>
</select>
Produces a list of meaningless months. To make it useful, you have to add an extra argument to mktime.
<?php
mktime(0,0,0,$i,1)
?>
24-Aug-2006 07:07
In response to the post by "nicky" on July 9, 2006:
Just so everyone's clear, if you have a date string formatted in a standard way, you'll probably want to go ahead and use PHP's built-in strtotime() function. The advantage to using nicky's str2time() function seems to be that you can specify how the date string you're passing in is formatted, so you can deal with non-standard date strings.
09-Jul-2006 01:08
here's a function to generate a timestamp from a certain date by using patterns:
<?php
function str2time($strStr, $strPattern = null)
{
// an array of the valide date characters, see: http://php.net/date#AEN21898
$arrCharacters = array(
'd', // day
'm', // month
'y', // year, 2 digits
'Y', // year, 4 digits
'H', // hours
'i', // minutes
's' // seconds
);
// transform the characters array to a string
$strCharacters = implode('', $arrCharacters);
// splits up the pattern by the date characters to get an array of the delimiters between the date characters
$arrDelimiters = preg_split('~['.$strCharacters.']~', $strPattern);
// transform the delimiters array to a string
$strDelimiters = quotemeta(implode('', array_unique($arrDelimiters)));
// splits up the date by the delimiters to get an array of the declaration
$arrStr = preg_split('~['.$strDelimiters.']~', $strStr);
// splits up the pattern by the delimiters to get an array of the used characters
$arrPattern = preg_split('~['.$strDelimiters.']~', $strPattern);
// if the numbers of the two array are not the same, return false, because the cannot belong together
if (count($arrStr) !== count($arrPattern)) {
return false;
}
// creates a new array which has the keys from the $arrPattern array and the values from the $arrStr array
$arrTime = array();
for ($i = 0;$i < count($arrStr);$i++) {
$arrTime[$arrPattern[$i]] = $arrStr[$i];
}
// gernerates a 4 digit year declaration of a 2 digit one by using the current year
if (isset($arrTime['y']) && !isset($arrTime['Y'])) {
$arrTime['Y'] = substr(date('Y'), 0, 2) . $arrTime['y'];
}
// if a declaration is empty, it will be filled with the current date declaration
foreach ($arrCharacters as $strCharacter) {
if (empty($arrTime[$strCharacter])) {
$arrTime[$strCharacter] = date($strCharacter);
}
}
// checks if the date is a valide date
if (!checkdate($arrTime['m'], $arrTime['d'], $arrTime['Y'])) {
return false;
}
// generates the timestamp
$intTime = mktime($arrTime['H'], $arrTime['i'], $arrTime['s'], $arrTime['m'], $arrTime['d'], $arrTime['Y']);
// returns the timestamp
return $intTime;
}
// example
$time = str2time('06-07-08 07:58:02', 'd-m-y H:i:s');
var_dump($time);
var_dump(date('d.m.Y H:i:s', $time));
?>
08-May-2006 01:40
Negative timestamps give problem also using linux as guest operating system inside WMvare with Windows host operating system.
21-Jan-2006 09:24
I read the above note and think up a simple way(just 10 lines) to find time difference in days, hrs, mins, secs!
In my way, we do not need to fix the format of time!
$starttime=time();
// the start time can change to =strtotime($endtime);
$endtime=strtotime($endtime);
//$endtime can be any format as well as it can be converted to secs
$timediff = $endtime-$starttime;
$days=intval($timediff/86400);
$remain=$timediff%86400;
$hours=intval($remain/3600);
$remain=$remain%3600;
$mins=intval($remain/60);
$secs=$remain%60;
//this code is copied from the other note!thx to that guy!
$timediff=$days.'days'.$hours.'hr'.$mins.'min'.$secs.'s';
Hope that it is usefull!
14-Nov-2005 09:21
A trivial way to avoid having to remember the quirky order of variables.
It's also more convenient to use because you can ignore the last three (time) variables if all you want to do is manupulate the date components.
Just include the following function at the top of your script and call ansi_mktime instead of mktime.
function ansi_mktime($y=0, $month=0, $d=0, $h=0, $min=0, $s=0){
return mktime($h, $min, $s, $month, $d, $y);
}
// eg:
$day = 14;
echo date("dS \d\a\y of M Y", ansi_mktime(2005, 11, $day + 7))
// output: 21st day of Nov 2005
08-Sep-2005 06:40
I needed a script to display a dropdown menu with a list of week ending dates. I wrote this as a result. I hope it helps somebody. The selname variable is the name of the select field and the day of week of the begining date designates the end of the week.
<?php
$selname="we_date";
//Build Begin date
$month=10;
$day=04;
$year=2003;
$hour=date('H');
$min=date('i');
$sec=date('s');
//convert it to unix timestamp
$bdate=mktime($hour,$min,$sec,$month,$day,$year);
//Build Today
$thour=date('H');
$tmin=date('i');
$tsec=date('s');
$tmonth=date('n');
$tday=date('d');
$tyear=date('Y');
//convert it to unix timestamp
$today=mktime($thour,$tmin,$tsec,$tmonth,$tday,$tyear);
//just the weeks
$nbdate=floor($bdate/(7 * 24 * 60 * 60));
$ntoday=floor($today/(7 * 24 * 60 * 60));
//difference between today and the beginning date
$diff=$today-$bdate;
echo "<select size='1' name='$selname'>\n";
while ($bdate <= $today+(7 * 24 * 60 * 60)){
echo ("<option value='".date('n/d/Y',$bdate)."'>
".date('n/d/Y',$bdate)."</option>\n");
$bdate=$bdate+(7 * 24 * 60 * 60);
}
echo "</select>";
?>
07-Aug-2005 12:25
In response to Hayden...
I hate to inform you of this after you've worked out your own function for date validation, but PHP has a function called checkdate(). It does the exact same thing as your isvaliddate() function.
22-Jul-2005 06:31
In response to phpprince at phpprince dot com:
The same thing can be done with
<?php
echo date('Y-m-d H:i:s', strtotime('+7 days'));
?>
08-Jun-2005 06:20
You may consider easier to calculate dates using strtotime() instead of mktime():
<?
date('Y-m-d',strtotime('now +'.$f.' months'));
?>
will produce the date $f($f>=0) months after today.
07-Jun-2005 02:33
Here is a quick way to check the a date is valid. I use this when I get users to enter dates via drop downs, which leave open the possibility for impossible dates like 30-Feb-2005 and 31-Jun-2005 etc. This is only necessary as mktime() will accept these invalid dates, which is, in my case, sometimes not the desired handling.
<?php
function isvaliddate($day, $month, $year) {
$day = intval($day);
$month = intval($month);
$year = intval($year);
$time = mktime(0,0,0,$month,$day,$year);
if ($day != date("j",$time)) return false;
if ($month != date("n",$time)) return false;
if ($year != date("Y",$time)) return false;
return true;
}
?>
Note that date("Y",$time) checks the year as a 4 digit year. That line could be replaced as shown below to allow for the 2 digit notation as well.
Also the order the arguments need to be specified is day, month, year, because I come from NZ and that is the format we use here. If you prefer another format, for example month, day, year, just change the order of the arguments on the first line.
<?php
function isvaliddate($day, $month, $year) {
$day = intval($day);
$month = intval($month);
$year = intval($year);
$time = mktime(0,0,0,$month,$day,$year);
if ($day != date("j",$time)) return false;
if ($month != date("n",$time)) return false;
if (($year != date("Y",$time)) AND ($year != date("y",$time))) return false;
return true;
}
?>
Hope this helps someone!
Cheers,
Hayden.
27-May-2005 03:40
cdblog at gmail dot com didn't clarify exactly what his function does: it returns the week number WITHIN THE CURRENT MONTH, i.e. the first day of the month is in week 1, the eighth day is in week 2, the fifteenth is in week 3, the 22nd is in week 4, and the 29th is in week 5. A useful function, if you need such things.
26-May-2005 11:06
<?php
/**
* @return int
* @desc get the week's No. by day.
* @link http://php.clickz.cn/articles/date/getWeekNoByDay,html
* @update at my php blog, http://php.clickz.cn/
*/
function getWeekNoByDay($year = 2005,$month = 5,$day = 5) {
return ceil(($day + date("w",mktime(0,0,0,$month,1,$year)))/7);
}
?>
27-Apr-2005 02:42
My little code for make a code to get the difference between dates
<?
$data1 = mktime (0,0,0,5,5,2005); //specify a date1
$data2 = mktime (0,0,0,5,15,2005); //specify a date2
$differenza = ($data2 - $data1 ) / 86400;
echo " The Different $data2 - data1 = $differenza";
?>
31-Mar-2005 08:48
If the month is greater than 12, it goes into the next year. If it is less than 1, it goes into the previous year. Generally, it behaves as you'd expect it to :-)
Examples:
<?php
// January 1, 2005
print date ("F j, Y", mktime (0,0,0,13,1,2004));
// December 1, 2003
print date ("F j, Y", mktime (0,0,0,0,1,2004));
// February 1, 2005
print date ("F j, Y", mktime (0,0,0,14,1,2004));
// November 1, 2003
print date ("F j, Y", mktime (0,0,0,-1,1,2004));
?>
11-Feb-2005 01:41
if you ever wondered how to convert a windows (ASP) Timestamp to an unix Timestamp, try this:
(windowsTime to unixTime):
function wT2uT($win_timestamp) {
$WIN_DATE_CONST=2209165200;
$WIN_TIME_CONST=115740.74074074;
list($win_date, $win_time)=explode(",",$win_timestamp);
$win_time=substr($win_time."0000000000",0,10);
$ux_date = $win_date*24*60*60;
$ux_date-= (date("I")*60*60);
$ux_date-= $WIN_DATE_CONST;
$ux_time = round($win_time/$WIN_TIME_CONST);
return($ux_date+$ux_time);
}
04-Feb-2005 01:42
I have to correct, what Evorg (28-Sep-2004 04:24) wrote. If you want to delete a cookie, simply take the value 0 (zero) as timestamp. It's the same as the timestamp, which Evorg's example generates.
01-Dec-2004 11:19
<?php
// Calculates UNIX timestamps from datestamps counting
// days from 01/01/0000. Used in some DataFlex databases.
// Tested only with Timestamps > 01/01/1970 and
// < 31/12/2025.
// Arguments: $days (Integer, days-from-0000,
// e.g. 731168 = 30/10/2001)
function date_diff_value($days) {
// 1/1/1970 = 719543 days counting from 01/01/0000
$day_1_1_1970 = 719543;
$diff = $days - $day_1_1_1970;
$unix_ts = $diff * 86400;
return $unix_ts;
}
?>
02-Nov-2004 10:03
Daylight saving time! Grrrrrrrrrr! (And a minor "Grrr!" for PHP making this less intuitive than it should be).
In brief, NEVER add number of seconds, like 60*60*24, but use strtotime("+1 day", $myDate)).
Some of the 'simple' functions above for calculating dates will NOT work correctly when a date includes daylight saving time. Shown below is the problem illustrated and a simple solution.
EXAMPLE 1: WRONG!
I had the following loop, which worked fine all year, until this weekend, when the clocks changed, and it broke! The problem is daylight saving time:
// Loop through dates adding 1 days worth of seconds each time
$myDate = 1098914400 // October 28th
for ($myDate = $fromDate; $myDate <= $toDate; $myDate = $myDate + 60 * 60 * 24) {
$printable = strftime("%d-%m-%Y %H:%M:%S", $myDate);
echo $printable
}
"28-10-2004 00:00:00"
"29-10-2004 00:00:00"
"30-10-2004 00:00:00"
"31-10-2004 00:00:00"
"31-10-2004 23:00:00" (oops! 31st October repeats and time now 23:00!!)
"01-11-2004 23:00:00"
"02-11-2004 23:00:00"
EXAMPLE 2: CORRECT!
$myDate = 1098914400 // October 28th
for ($myDate = $fromDate; $myDate <= $toDate; $myDate = strtotime("+1 day", $myDate)) {
$printable = strftime("%d-%m-%Y %H:%M:%S", $myDate);
echo $printable
}
"28-10-2004 00:00:00"
"29-10-2004 00:00:00"
"30-10-2004 00:00:00"
"31-10-2004 00:00:00"
"01-11-2004 00:00:00"
"02-11-2004 00:00:00"
28-Sep-2004 04:24
mktime should be used when removing cookies. Normally people tend to use: time()-3600 to set the expiration date in "the past". The problem with this is that some computers is set at a wrong date and therfore differs from the server-time. That will render the time()-3600 unusable.
Instead use mktime(12,0,0,1, 1, 1990) as you expiration criteria. I'm convinced that only a very few users has set their time back more than 1990 :)
14-Sep-2004 11:27
A simple statement to calculate days between two dates
$dayselepsed = round((strtotime($dateone) - strtotime($datetwo))/(60*60*24)-1);
Regards Alex Curvers
25-Jun-2004 02:36
Hi,
For those looking for a solution to the 1970-2038 limitation, the adodb time library does the trick nicely. The website has changed, to
http://phplens.com/phpeverywhere/adodb_date_library
"This library replaces native functions as follows:
getdate() with adodb_getdate()
date() with adodb_date()
gmdate() with adodb_gmdate()
mktime() with adodb_mktime()
gmmktime() with adodb_gmmktime()"
Download the inc file:
http://phplens.com/lens/dl/adodb-time.zip
Enjoy, John Lim
13-May-2004 05:42
bichinhoverde's my_gmmktime function uses an incomplete definition of leap year. It's not leap year if the year is divisible by 100 and NOT divisible by 400. E.G. 2000 was a leap year, but 2100 will not be. Trivial, but it should be said.
Thus,
if ( $i % 4 == 0 ) {
$output += 24*60*60;
}
should be:
if ( (($i % 4 == 0) && ($i % 100 != 0))
|| ($i % 400 == 0) ) {
$output += 24*60*60;
}
23-Apr-2004 02:27
I noticed that while it is legal to do this:
$date=date("Y-m-d", mktime(0,0,0,4,20,2004);
It doesn't quite work the same when you do this:
$time=date("H:i:s", mktime(10,30,15,0,0,0);
No matter what variables you put in for time, it'll always spit out 15:59:59. You need to include the month, day and year if you want it to convert the time.
I spent nearly an hour trying to figure out what I was doing wrong til I stuck in a random date.
08-Apr-2004 01:58
For those looking for a solution to the 1970-2038 limitation, the adodb time library does the trick nicely.
http://php.weblogs.com/adodb_date_time_library
"This library replaces native functions as follows:
getdate() with adodb_getdate()
date() with adodb_date()
gmdate() with adodb_gmdate()
mktime() with adodb_mktime()
gmmktime() with adodb_gmmktime()"
Download the inc file:
http://phplens.com/lens/dl/adodb-time.zip
Enjoy,
rob
28-Mar-2004 08:48
As Nigel pointed out, you should be aware of DST (Daylight Savings Time) when using mktime(). Some systems will return a negative value if you use 0 as the hour, as it will simply skip from (for example) 23:59:59 to 01:00:00. Instead use 12 (noon) as the hour and you won't get a negative timestamp or a date in the 1960's.
This code will work with DST:
$today = mktime(12, 0, 0, date("m"), date("d"), date("Y"));
28-Feb-2004 04:30
I find it easiest, if I want to find you how many days there are between two dates to use the following method:
$init_day = 1;
$init_mth = 1;
$init_yr = 2004;
$dst_day = 5;
$dst_mth = 8;
$dst_yr = 2004;
//first convert to unix timestamp
$init_date = mktime(12,0,0,$init_mth,$init_day,$init_yr);
$dst_date = mktime(12,0,0,$init_mth,$init_day,$init_yr);
$offset = $dst_date-$init_date; //Depending on which offset type you want, switch order
$days = floor($offset/60/60/24);
15-Feb-2004 09:15
Several posts here offer procedures to compute the number of days between two dates based on using mktime, using the given date and 00:00:00 as the time. It turns out that this is bad choice for the default time for such calculations when the date in question happens to be the date when daylight savings time starts. For example, on several OSs, there is no such time as 00:00:00 30-03-2003 (and mktime returns a negative value), because the clock changed from 23:59:59 29-03-2003 straight to 01:00:00 30-03-2003 as a result of Daylight Saving. At better choice is to use, for example, 12,0,0,30,3,2003 as the argument to mktime, that is, use noon, not midnight as the default time.
01-Feb-2004 09:44
Consider skipping months with mktime().
$nextmonth = date("M",mktime(0,0,0,date("n")+1,date("j"),date("Y")));
On any day in Januari you expect to get Feb, right?
But on January 30th you'll get Mar. It will try Feb 30th, which doesn't exist, and skips another month. Therefore in this case present a day value that will certainly be legal in any month, like day "1".
This will give you next month on any day of the year:
$nextmonth = date("M",mktime(0,0,0,date("n")+1,1,date("Y")));
09-Dec-2003 04:49
In the above example it should ne boted that if you try to calculate the command at midnight on the 28/04/2004 you will get an erroneous response. This has been driving me to distraction.
$myTime = mktime( 0, 0, 0, 3, 28, 2004);
Solution I found was to create the time at 3am well after the 2am daylight savings problem, viz:
$myTime = mktime( 3, 0, 0, 3, 28, 2004);
Not sure if this is documented anywhere.
24-Nov-2003 02:36
Very often we are faced with the problem of adjusting ourself to local time where application is running rather than running our application at server time.
Now we have a way to do that by setting TZ variable using putenv() method. But due to the non-availability of standard time zone codes, developers are often faced with the ambiguity of how to implement a non standard time zone(those which are not too popular)
I figured a way out myself for this. It uses the information that a particular time zone is n hours ahead or n hours behind standard GMT time zone.
here is what i did.
<?php
$day=15;
$month=12;
$year=2003;
//convert it to unix timestamp
$deadline=mktime('','','',$month,$day,$year);
//caluculate our time from GMT time
$hour=gmdate('H');
$min=gmdate('i');
$sec=gmdate('s');
$month=gmdate('n');
$day=gmdate('d');
$year=gmdate('Y');
$stamp=mktime ($hour,$min,$sec,$month,$day,$year);
// technique is to convert the GMT date & time to unix stamp, then convert time zone
//specific information like add 5 hours or subtract 5 hours to seconds,(consider day
//light saving here), and add/subtract it to the unix time stamp and then convert
//it back to date using date function if needed or perform operations needed on the
// time stamp
//subtract 6/n hours from GMT time (Central standard time/CST)
//vary this part to whatever time zone you are at
$do=6*60*60;
$lstamp=$stamp-$do;
echo("Today(local date/Central):".date('h:i:s d/n/Y',$lstamp)."<br>");
$left=$deadline-$lstamp;
$days_left=floor($left/(24 * 60 * 60));
$hours_left=floor($left/(60 * 60 ));
echo "<br>Days Left: $days_left<br>";
echo "<br>Hours Left(approx): $hours_left<br>";
?>
Change the $do variable to whatever seconds you are different from GMT and add or subtract accordingly to generate $lstamp.
This would solve your time zone problems.
Happy Coding,
Suneel Kanuri
20-Nov-2003 09:06
I think it is important to note that the timestamp returned is based upon the number of seconds from the epoch GMT, and then modified by the time zone settings on the server.
Thus...
mktime(0,0,0,1,1,1970) will not always return 0. For example with the US eastern time zone (GMT-5) will return 18000 (5 hours past the epoch) and the same function with the time zone set to the US pacific time zone (GMT-8) will return 28800 (8 hours past the epoch).
In an instance where you want time zone independence, you should use the function gmmktime()
18-Nov-2003 05:42
With regard to Example 1 and using mktime to correct out-of-range input.
It should be noted that mktime will implement day light saving amends. Consider the following:
<?
print(date("d/m/Y H:i:s",mktime(0,0,0,3,(27 + 1),2004)));
?>
OUTPUT "28/03/2004 02:00:00"
<?
print(date("d/m/Y H:i:s",(mktime(0,0,0,3,27,2004) + (((1 * 24) * 60) * 60))));
?>
OUTPUT "28/03/2004 00:00:00"
Dependent on your requirements this may or may be desirable