2009-10-05 18:11:08
2009-10-05 18:07:13
Це повинно генерувати 235, як це зробити?
Відповіді:
Ви можете використовувати strtotime () для цього:
$diff = strtotime('2009-10-05 18:11:08') - strtotime('2009-10-05 18:07:13')
Подібний підхід можливий з об'єктами DateTime, наприклад
$date = new DateTime( '2009-10-05 18:07:13' );
$date2 = new DateTime( '2009-10-05 18:11:08' );
$diff = $date2->getTimestamp() - $date->getTimestamp();
date()для отримання дати і часу зараз ( date("Y-m-d H:i:s")).
З об'єктами DateTime ви можете зробити це так:
$date = new DateTime( '2009-10-05 18:07:13' );
$date2 = new DateTime( '2009-10-05 18:11:08' );
$diffInSeconds = $date2->getTimestamp() - $date->getTimestamp();
Посилання на час дати PHP корисно для таких речей: Функції часу часу PHP
strtotime () - це, мабуть, найкращий спосіб.
$seconds = strtotime('2009-10-05 18:11:08') - strtotime('2009-10-05 18:07:13')
Через обмеження епохи unix у вас можуть виникнути проблеми зі порівнянням дат до 1970 року і після 2038 року. Я вирішив втратити точність (= не дивитись ні на одну секунду), але уникати переходу через перетворення епох unix (getTimestamp). Це залежить від того, що ти робиш, щоб робити ...
У моєму випадку використання 365 замість (12 * 30) та "30" як середньої довжини місяця зменшило помилку в корисному виведенні.
function DateIntervalToSec($start,$end){ // as datetime object returns difference in seconds
$diff = $end->diff($start);
$diff_sec = $diff->format('%r').( // prepend the sign - if negative, change it to R if you want the +, too
($diff->s)+ // seconds (no errors)
(60*($diff->i))+ // minutes (no errors)
(60*60*($diff->h))+ // hours (no errors)
(24*60*60*($diff->d))+ // days (no errors)
(30*24*60*60*($diff->m))+ // months (???)
(365*24*60*60*($diff->y)) // years (???)
);
return $diff_sec;
}
Зверніть увагу, що помилка може становити 0, якщо "середні" величини призначені для різниці. Документи PHP не говорять про це ... У поганому випадку помилка може бути:
Я вважаю за краще припустити, що хтось вирішив вважати "m" 30 днями, а "y" 365, заряджаючи "d" з різницею, коли "diff" проходить через не 30-денні місяці ...
Якщо хтось знає щось більше про це і може надати офіційну документацію, ласкаво просимо!
Якщо вам потрібна реальна місцева різниця в часі і ви хочете працювати getTimestamp, ви повинні враховувати переходи на літній час протягом розрахункового періоду. Отже, місцеве зміщення до UTC має бути включене в рівняння.
Візьмемо, наприклад, такі дати:
$tz = new \DateTimeZone("Europe/Berlin");
$start = new \DateTime("2018-02-01 12:00:00", $tz);
$end = new \DateTime("2018-04-01 12:00:00", $tz);
$startв UTC є "2018-02-01 11:00:00", а в UTC $end- "2018-04-01 10:00:00". Зауважте, що, хоча час доби однаковий у часовому поясі Берліна, в UTC він інший. Зсув UTC становить одну годину $startі 2 години $end.
Майте на увазі, що getTimestampзавжди повертається UTC! Тому ви повинні відняти зміщення від позначки часу, коли шукаєте фактичну локальну різницю.
// WRONG! returns 5094000, one hour too much due to DST in the local TZ
echo $end->getTimestamp() - $start->getTimestamp();
// CORRECT: returns 5090400
echo ($end->getTimestamp() - $end->getOffset()) - ($start->getTimestamp() - $start->getOffset());
Для тих, хто турбується про обмеження використання позначок часу (тобто використання дат до 1970 року і після 2038 року), ви можете просто обчислити різницю в секундах так:
$start = new DateTime('2009-10-05 18:11:08');
$end = new DateTime('2009-10-05 18:07:13');
$diff = $end->diff($start);
$seconds = ($diff->format('%r%a') * 24 * 60 * 60)
+ $diff->h * 60 * 60
+ $diff->i * 60
+ $diff->s;
echo $seconds; // output: 235
Просте і точне рішення (на прикладі коментаря Nilz11):
$hiDate = new DateTime("2310-05-22 08:33:26");
$loDate = new DateTime("1910-11-03 13:00:01");
$diff = $hiDate->diff($loDate);
$secs = ((($diff->format("%a") * 24) + $diff->format("%H")) * 60 +
$diff->format("%i")) * 60 + $diff->format("%s");