PHP에서 두 datetime 사이의 간격 초를 얻습니까?


답변:


138

이를 위해 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();

1
참고 : "낮은"시간이 "지금" date()이고을 사용 하여 지금의 날짜 / 시간을 가져 오는 데 사용 하는 경우 시간 (24 시간 모드)에 대문자 "H"를 사용해야 합니다 date("Y-m-d H:i:s").
jave.web

```m / d / y 또는 dmy 형식의 날짜는 다양한 구성 요소 사이의 구분 기호를 보면 명확 해집니다. 구분 기호가 슬래시 (/)이면 미국식 m / d / y로 간주됩니다. 구분자가 대시 (-) 또는 점 (.) 인 경우 유럽 dmy 형식이 가정됩니다. 그러나 연도가 두 자리 형식으로 제공되고 구분 기호가 대시 (-, 날짜 문자열은 ymd로 구문 분석 됨) 인 경우 잠재적 인 모호성을 방지하려면 ISO 8601 (YYYY-MM-DD) 날짜를 사용하거나 DateTime :: createFromFormat () 가능한 경우```
Nikola Petkanski

JCM 답변 확인 및 사례 선택
Leandro

158

DateTime 개체를 사용하면 다음과 같이 할 수 있습니다.

$date = new DateTime( '2009-10-05 18:07:13' );
$date2 = new DateTime( '2009-10-05 18:11:08' );

$diffInSeconds = $date2->getTimestamp() - $date->getTimestamp();

1
이것은 또한 일광 절약 시간을 고려합니다!
Brainware

5
이것은 질문에 대한 가장 우아한 해결책입니다. 이것은 받아 들여진 대답이어야합니다.
Giel Berkers

1
일광 절약 시간제를 올바르게 고려하려면 올바른 DateTimeZone을 제공해야합니다. 시스템이 올바르게 설정되어 있다면 php는 이미 시스템 기본값에서 시간대를 알고있을 수 있습니다. 문제가있는 경우 다음과 같이 수동으로 인스턴스화하십시오. $ tz = new DateTimeZone ( 'Europe / Berlin'); 두 번째 매개 변수로 DateTime 생성자에 전달합니다.
j4k3

훌륭한 솔루션이지만 더 오랜 기간 동안 (예 : 1 시간) 음수 값 (오버플로?)을받습니다.이 문제를 해결하는 방법은 무엇입니까?
marto 19-06-02

8

PHP 날짜 시간 참조는 다음과 같은 경우에 유용합니다. PHP 날짜 시간 함수

strtotime () 이 아마도 가장 좋은 방법 일 것입니다.

$seconds = strtotime('2009-10-05 18:11:08') - strtotime('2009-10-05 18:07:13')

4

유닉스 시대의 제한으로 인해 1970 년 이전과 2038 년 이후의 날짜를 비교하는 데 문제가있을 수 있습니다. 저는 정밀도를 느슨하게 선택하고 (= 1 초를 보지 않음) 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 문서는 이것에 대해 말하지 않습니다 ... 나쁜 경우 오류는 다음과 같습니다.

  • 1 개월 미만의 시간 간격에 diff가 적용되는 경우 0 초
  • 1 개월을 초과하는 시간차에 diff가 적용되는 경우 0 ~ 3 일
  • 1 년을 초과하는 시간 간격에 diff가 적용되는 경우 0 ~ 14 일

나는 누군가가 "m"을 30 일로, "y"를 365로 간주하고 "diff"가 30 일이 아닌 달을 걸을 때 차이를 "d"로 청구했다고 가정하는 것을 선호합니다.

누군가 이것에 대해 더 알고 있고 공식 문서를 제공 할 수 있다면 환영합니다!


d 속성 대신 days 속성을 사용하여 두 날짜 사이의 정확한 날짜를 가져옵니다. 따라서 부정확 한 결과가 없습니다.
Nilz11 2016

2
strtotime("2009-10-05 18:11:08") - strtotime("2009-10-05 18:07:13")

2

실제 현지 시차가 필요하고으로 작업하려는 getTimestamp경우 계산 된 기간 동안 DST 스위치를 고려해야합니다. 따라서 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);

$startUTC로 "2018-02-01 11:00:00"이고 UTC $end로 "2018-04-01 10:00:00"입니다. 베를린 시간대에서는 시간이 동일하지만 UTC에서는 다릅니다. UTC 오프셋은에서 1 시간,에서 $start2 시간입니다 $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());

이 대답은 끔찍한 잘못된 정보입니다. 나는 이것을 확인하기 위해 내 자신의 테스트 케이스를 작성했으며 그것이 완전히 잘못되었다는 것이 기쁩니다. 5094000 % 86400 = 82800. 시계가 DST 경계에서 한 시간 앞으로 건너 뛰는 "누락 된 시간"에 대해 하루 종일에서 3600을 뺀 값입니다. 더 간단한 테스트 사례 : '2019-03-31 01:59:59'와 '2019-03-31 03:00:01'간의 타임 스탬프 차이는 2 초로 정확한 양입니다. '2019-10-27 01:59:59'와 '2019-10-27 02:00:01'간의 타임 스탬프 차이는 3602 초로 정확한 양입니다.
j4k3

이에 대한 추가 정보 : getTimestamp 및 setTimestamp는 항상 시간대없는 유닉스 타임 스탬프를 참조 합니다 . 시간대 자유 형식을 시간대 오프셋과 혼합하고 있습니다. "유닉스 타임 스탬프 처리"예제에서는 시계가 2 시간이 아닌 1 시간 뒤로 다이얼되기 때문에 3600 + 1 = 3720 초를 찾고 있습니다.
j4k3

0

타임 스탬프 사용의 한계 (즉, 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

블로그 게시물 더 읽기에 관심이있는 사람들을 위해입니다.


-1

간단하고 정확한 솔루션 (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");
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.