|
php.net | support | documentation | report a bug | advanced search | search howto | statistics | random bug | login |
[2021-02-13 20:45 UTC] palansher at outlook dot com
Description:
------------
DateTime->diff returns different days, depending on how many seconds passed from midnight on a target date.
This behaviour is independent of timezone settings.
Tested on PHP 7.2-7.4
The bug doesn't appear if you use short period:
<?php
$beforDate=DateTime::createFromFormat('Y-m-d G:i:s', '1900-01-01 00:00:00');
$afterDate=DateTime::createFromFormat('Y-m-d G:i:s', '1900-01-08 00:00:43');
$dtInterval = $beforDate->diff($afterDate);
$daysPassed = $dtInterval->days;
echo "days passed if target date have 42 seconds from midnight: $daysPassed" . PHP_EOL;
$afterDate=DateTime::createFromFormat('Y-m-d G:i:s', '1900-01-08 00:00:43');
$dtInterval = $beforDate->diff($afterDate);
$daysPassed = $dtInterval->days;
echo "days passed if target date have 43 seconds from midnight: $daysPassed" . PHP_EOL;
Test script:
---------------
<?php
$beforDate=DateTime::createFromFormat('Y-m-d G:i:s', '1900-01-01 00:00:00');
$afterDate=DateTime::createFromFormat('Y-m-d G:i:s', '2021-01-08 00:00:42');
$dtInterval = $beforDate->diff($afterDate);
$daysPassed = $dtInterval->days;
echo "days passed if target date have 42 seconds from midnight: $daysPassed" . PHP_EOL;
$afterDate=DateTime::createFromFormat('Y-m-d G:i:s', '2021-01-08 00:00:43');
$dtInterval = $beforDate->diff($afterDate);
$daysPassed = $dtInterval->days;
echo "days passed if target date have 43 seconds from midnight: $daysPassed" . PHP_EOL;
Expected result:
----------------
days passed: 44201
Actual result:
--------------
days passed: 44202
PatchesPull RequestsHistoryAllCommentsChangesGit/SVN commits
|
|||||||||||||||||||||||||||
Copyright © 2001-2025 The PHP GroupAll rights reserved. |
Last updated: Sun Oct 26 22:00:01 2025 UTC |
Just realized: This error appears if default timezone set, like date_default_timezone_set('Europe/Moscow'); But timezone must not affect the result. corrected code: date_default_timezone_set('Europe/Moscow'); $beforDate=DateTime::createFromFormat('Y-m-d G:i:s', '1900-01-01 00:00:00'); $afterDate=DateTime::createFromFormat('Y-m-d G:i:s', '2021-02-08 00:00:42'); $dtInterval = $beforDate->diff($afterDate); $daysPassed = $dtInterval->days; echo "1. days passed if target date have 42 seconds from midnight: $daysPassed" . PHP_EOL; $afterDate=DateTime::createFromFormat('Y-m-d G:i:s', '2021-02-08 00:00:43'); $dtInterval = $beforDate->diff($afterDate); $daysPassed = $dtInterval->days; echo "2. days passed if target date have 43 seconds from midnight: $daysPassed" . PHP_EOL; result: 1. days passed if target date have 42 seconds from midnight: 44232 2. days passed if target date have 43 seconds from midnight: 44233requinix@php.net, you are right. The date_default_timezone_set('Europe/Moscow'); was set. But!! a year has the same number of days in any timezone. How timezone can affect the total days number?Found another incorrect behaviour: $beforDate=DateTime::createFromFormat('Y-m-d G:i:s', '1900-01-01 00:00:00'); $beforDate->setTimezone(new DateTimeZone('UTC')); $afterDate=DateTime::createFromFormat('Y-m-d G:i:s', '2021-02-08 00:00:00'); $afterDate->setTimezone(new DateTimeZone('UTC')); $dtInterval = $beforDate->diff($afterDate); $daysPassed = $dtInterval->days; echo "1. days passed: $daysPassed" . PHP_EOL; $afterDate=DateTime::createFromFormat('Y-m-d G:i:s', '2021-02-08 00:50:00'); $afterDate->setTimezone(new DateTimeZone('UTC')); $dtInterval = $beforDate->diff($afterDate); $daysPassed = $dtInterval->days; echo "1. days passed if 50 minutes added to target date: $daysPassed" . PHP_EOL; Have output: days passed: 44232 days passed if 50 minutes added to target date: 44233 https://3v4l.org/49Dv0