5

I think I am fully aware of ISO 8601 and that the first week of a year is the week that has a Monday in it. However I came across a strange behavior in PHP (5.6) DateTime Class.

Here is my code:

$start = new DateTime('2009-01-01 00:00');
$end = new DateTime();
$point = $start;

while($point <= $end){
   echo $point->format('YW');
   $point = $point->modify('next week');
}

This puts out correctly

200901
200902
200903
...

But if I pick as a start date something earlier in 2008 like $start = new DateTime('2008-01-01 00:00'); then I get a different result:

...
200852
200801 // <=== 2008??
200902   
200903
...

Is this a PHP bug or am I'm missing something here?

Steven M
  • 574
  • 4
  • 20
  • its because it first week of 2009, try `echo $point->format('YW') ." --> ". $point->format('Y-m-d');` hope you will understand the thing – Chetan Ameta Jul 07 '16 at 12:42

2 Answers2

4

Tinkered with this and finally figured it out

$start = new DateTime('2008-12-29 00:00');
$end = new DateTime('2009-01-7 00:00');
$point = $start;

while($point <= $end){
   echo $point->format('YW') . "\t";
   echo $point->format('m-d-Y')  . "\n";
   $point = $point->modify('next week');
}

So the first date here is 2008-12-29. Thus Y is correct. But 2008-12-29 is also week 1. So the W is also correct

https://3v4l.org/JZtqa

Machavity
  • 30,841
  • 27
  • 92
  • 100
  • Then this is a PHP bug. If you iterate through a year by weeks you would expect it to correctly calculate the 53rd week, right? – Steven M Jul 07 '16 at 12:49
  • 2
    @StevenM It's not a bug. That's actually how ISO8601 sees it. [Check out this Wikipedia article](https://en.wikipedia.org/wiki/ISO_week_date) and you'll note that `Mon 29 Dec 2008` is `2009-W01-1` – Machavity Jul 07 '16 at 12:54
  • Yes, exactly - but PHP makes that the first week in *2008* not 2009.... – Steven M Jul 07 '16 at 12:55
  • 3
    @StevenM No. 12-29-2008 is still in 2008. That's what `Y` does. If you use `o` instead (ISO8601 year) you'll see it's in 2009. The bug is in your script, not PHP https://3v4l.org/nEMmj – Machavity Jul 07 '16 at 12:59
0

It's not a bug! Inspired by @Machavity and based on this this similar question I found a solution:

echo $point->format('oW');

instead of

echo $point->format('YW')

produces:

...
200852
200901
200902
...

no matter when the start date is. It's really a RTM case, as the PHP manual states:

o ==> ISO-8601 year number. This has the same value as Y, except that if the ISO week number (W) belongs to the previous or next year, that year is used instead. (added in PHP 5.1.0)

Community
  • 1
  • 1
Steven M
  • 574
  • 4
  • 20