Problem with php strtotime function when using ordinal values

I ever get unexpected results when using ordinal values ​​with strtotime. For example, why

date("M j", strtotime("second Tuesday February 2011")) 

will lead to β€œFeb 15” (which is actually third on Tuesday in 2011?

+4
source share
3 answers

It seems unsafe to rely on strtotime to handle ordinary dates - at least in PHP versions <5.3. (I tested with 5.2.9 and 5.2.11 and none of them worked, despite the requirement in the online documentation that the error was fixed in 5.2.7.)

Adding "from", as suggested, apparently only works in php 5.3+, and generally speaking, bypassing the ordinal will return the "first" event, but other ordinals will be for 7 days.

The best solution for PHP 5.2 is something like this:

 $recurrOrdinal = "last"; $dayOfWeek = "Thursday"; $monthYear = "March 2011"; echo ordinalDate($recurrOrdinal, $dayOfWeek, $monthYear); function ordinalDate($recurrOrdinal, $dayOfWeek, $monthYear) { $firstDate = date("j", strtotime($dayOfWeek . " " . $monthYear) ); if ($recurrOrdinal == "first") $computed = $firstDate; elseif ($recurrOrdinal == "second") $computed = $firstDate + 7; elseif ($recurrOrdinal == "third") $computed = $firstDate + 14; elseif ($recurrOrdinal == "fourth") $computed = $firstDate + 21; elseif ($recurrOrdinal == "last") { if ( ($firstDate + 28) <= date("t", strtotime($monthYear)) ) $computed = $firstDate + 28; else $computed = $firstDate + 21; } return date("Ymd", strtotime($computed . " " . $monthYear) ); } 
0
source

You are missing the 'of'.

$ php -r 'echo date ("M j", strtotime ("second Tuesday, February 2011")); February 15

$ php -r 'echo date ("M j", strtotime ("second Tuesday of February 2011")); February 8th

PHP version:

$ php -v
PHP 5.3.3 (cli) (built: August 22, 2010 19:41:55)
Copyright (c) 1997-2010 PHP Group
Zend Engine v2.3.0, Copyright (c) 1998-2010 Zend Technologies

The documentation tells you the reason for this:

Also note that the "from" to "ordinal space dayname space 'of'" and "last" space dayname space 'of' "does something special.

  • It sets the day of the month to 1.
  • "day ordinal" from "" go to another day. (Example: "first Tuesday of July 2008" means "2008-07-01").
  • "day ordinal" go to another day. (Example: β€œfirst Tuesday, July 2008” means β€œ2008-07-08”, see also item 4 in the list above).
+5
source

The manual for strtotime () tells you what you are looking for

In PHP 5 to 5.2.7, querying given the occurrence of a given business day per month, when on this weekday the first day of the month incorrectly add one week to the returned timestamp. This has been fixed in 5.2.7 and later.

In short, this is a bug in the version you are using.

If you are looking for some applicable fix, it seems that dropping the ordinal value works (as if the first / second / third indicates full weeks)

 echo date("M j", strtotime("Tuesday February 2011")), '<br>'; echo date("M j", strtotime("first Tuesday February 2011")), '<br>'; echo date("M j", strtotime("second Tuesday February 2011")), '<br>'; echo date("M j", strtotime("third Tuesday February 2011")), '<br>'; 
+2
source

Source: https://habr.com/ru/post/1337046/


All Articles