note 77281 added to ref.datetime

From: Date: Wed, 22 Aug 2007 22:02:40 +0000
Subject: note 77281 added to ref.datetime
Groups: php.notes 
Request: Send a blank email to php-notes+get-129710@lists.php.net to get a copy of this message
This will calculate the duration between two arbitrary dates that are valid within the given unix timestamp range. It also takes care of leap years, that is, if the minimum date is a leap year and the beginning month is February it will take into account the leap days, if any. The below routine assumes that you a DateTime object that supports the following methods: getYear(), getMonth(), getDayOfMonth(), getHourOfDay(), getMinuteOfHour(), and getSecondOfMinute() Adapt as you wish. ---8<--- snip --->8--- $min = DateTime::fromString( "1980-02-01 01:01:00" ); $max = DateTime::fromString( "2004-01-02 14:10:00" ); echo "min: " . $min . "<br>"; echo "max: " . $max . "<br>"; $rtmcorr = 0; // TM correction $rthcorr = 0; // TH correction $rdcorr = 0; // D correction $rmcorr = 0; // M correction $rycorr = 0; // Y correction $my = $max->getYear(); $mm = $max->getMonth(); $md = $max->getDayOfMonth(); $mth = $max->getHourOfDay(); $mtm = $max->getMinuteOfHour(); $mts = $max->getSecondOfMinute(); $ny = $min->getYear(); $nm = $min->getMonth(); $nd = $min->getDayOfMonth(); $nth = $min->getHourOfDay(); $ntm = $min->getMinuteOfHour(); $nts = $min->getSecondOfMinute(); $ry = 0; $rm = 0; $rd = 0; $rth = 0; $rtm = 0; $rts = 0; // rts if ( $my == $ny && $mm == $nm && $md == $nd && $mth == $nth && $mtm == $ntm ) { $rts = $mts - $nts; } else { $rts = 60 - ( $nts == 0 ? 60 : $nts ) + $mts; $rtmcorr = $rts == 0 ? 0 : ( $rts > 60 ? 1 : -1 ); $rts = $rts % 60; } echo "rts: " . $rts . "<br>"; echo "rtmcorr: " . $rtmcorr . "<br>"; // rtm if ( $my == $ny && $mm == $nm && $md == $nd && $mth == $nth ) { $rtm = $mtm - $ntm + $rtmcorr; } else { $rtm = 60 - ( $ntm == 0 ? 60 : $ntm ) + $mtm; $rtmcorr = $rtm == 0 ? 0 : ( $rtm > 60 ? 1 : -1 ); $rtm = $rtm % 60; } echo "rtm: " . $rtm . "<br>"; echo "rthcorr: " . $rthcorr . "<br>"; // rth if ( $my == $ny && $mm == $nm && $md == $nd ) { $rth = $mth - $nth + $rthcorr; } else { $rth = 24 - ( $nth == 0 ? 24 : $nth ) + ( $md - $nd ) * 24 + $mth + $rthcorr; $rdcorr = $rth == 0 || $rth > 24 ? 0 : -1; //( $rth > 24 ? 0 : -1 ); $rth = $rth % 24; } echo "rth: " . $rth . "<br>"; echo "rdcorr: " . $rdcorr . "<br>"; $isLeapYear = ( $ny % 4 == 0 || $ny % 100 == 0 ) && ! ( $ny % 400 == 0 ); $daysInMonthCorrection = $nm == 2 ? ( $isLeapYear ? -1 : -2 ) : ( $nm == 8 ? 1 : ( $nm % 2 == 0 ? 0 : 1 ) ); $daysInMonth = 30 + $daysInMonthCorrection; echo "daysInMonth: " . $daysInMonth . "<br>"; echo "daysInMonthCorrection: " . $daysInMonthCorrection . "<br>"; $doff = 0; $mcorr = 0; if ( $my == $ny && $mm == $nm ) { $rd = $md - $nd + $rdcorr; } else { $rd = $daysInMonth - ( $nd == 1 ? $daysInMonth + 1 : $nd ) + $md + $rdcorr; $rmcorr = $rd == 0 ? 0 : ( $rd > $daysInMonth ? 1 : -1 ); $rd = $rd % $daysInMonth; } echo "rd: " . $rd . "<br>"; echo "rmcorr: " . $rmcorr . "<br>"; $moff = 0; $ycorr = 0; if ( $my == $ny ) { $rm = $mm - $nm + $mcorr; } else { $rm = 12 - ( $nm == 1 ? 13 : $nm ) + $mm + $mcorr; $rycorr = $rm == 0 ? 0 : ( $rm > 12 ? 1 : -1 ); $rm = $rm % 12; } echo "rm: " . $rm . "<br>"; echo "rycorr: " . $rycorr . "<br>"; $ry = $my - $ny + $rycorr; echo "ry: " . $ry . "<br><br>"; echo "result: $ry-$rm-$rd $rth:$rtm:$rts"; This will yield: min: 01.02.1980 01:01:00 max: 02.01.2004 14:10:00 rts: 0 rtmcorr: 0 rtm: 9 rthcorr: 0 rth: 13 rdcorr: 0 daysInMonth: 29 daysInMonthCorrection: -1 rd: 1 rmcorr: -1 rm: 11 rycorr: -1 ry: 23 result: 23-11-1 13:9:0 Hope this helps. If there are any bugs, please feel free to contact me and we will surely get it straight the next time ;-) ---- Server IP: 69.147.83.197 Probable Submitter: 87.79.48.197 ---- Manual Page -- http://www.php.net/manual/en/ref.datetime.php Edit -- https://master.php.net/note/edit/77281 Del: integrated -- https://master.php.net/note/delete/77281/integrated Del: useless -- https://master.php.net/note/delete/77281/useless Del: bad code -- https://master.php.net/note/delete/77281/bad+code Del: spam -- https://master.php.net/note/delete/77281/spam Del: non-english -- https://master.php.net/note/delete/77281/non-english Del: in docs -- https://master.php.net/note/delete/77281/in+docs Del: other reasons-- https://master.php.net/note/delete/77281 Reject -- https://master.php.net/note/reject/77281 Search -- https://master.php.net/manage/user-notes.php

« previous php.notes (#129710) next »