PHP Strtotime -1month -2month

Вчера это работало нормально, без изменений.

echo date("M", strtotime("-3 month", time()) ); echo date("M", strtotime("-2 month", time()) ); echo date("M", strtotime("-1 month", time()) ); echo date("M", time()); 

Вывод, который он производил вчера, был таким, каким вы ожидали, например, Apr, May, Jun, Jul

Сегодня это повторяет май май июль июль

Есть идеи?

Заранее спасибо.

Это может быть связано с ошибкой # 44073

Вы можете попробовать что-то вроде этого:

 echo date("M", strtotime("-3 month", strtotime(date("F") . "1")) ) . "\n"; echo date("M", strtotime("-2 month", strtotime(date("F") . "1")) ) . "\n"; echo date("M", strtotime("-1 month", strtotime(date("F") . "1")) ) . "\n"; echo date("M", time()) . "\n"; 

(Решение найдено в разделе комментариев strtotime , прямая ссылка )

И выход:

 Apr May Jun Jul 

Вид «обмана» с форматом даты и именем месяца и всем этим …

Горден правильно определил проблему, но я хотел дать другое решение, которое было бы полезным, а не техническим. Просто используйте «первый день» или «последний день» в своем strtotime. Например, следующие примеры преодолевают проблему 31-го месяца:

 // Today is May 31st //All the following return 2012-04-30 echo date('Ym-d', strtotime("last day of -1 month")); echo date('Ym-d', strtotime("last day of last month")); echo date_create("last day of -1 month")->format('Ym-d'); // All the following return 2012-04-01 echo date('Ym-d', strtotime("first day of -1 month")); echo date('Ym-d', strtotime("first day of last month")); echo date_create("first day of -1 month")->format('Ym-d'); 

Попробуйте это вместо strtotime :

 mktime(0, (date("n") - 3 + 12) % 12, 1) 

Идея состоит в том, чтобы взять текущий номер месяца ( date("n") ), вычесть количество месяцев от него, которое вы хотите (здесь -3 ), добавить 12 к нему, а затем получить по модулю 12.

Это известное и ожидаемое поведение. Причина этого в том, что месяц является относительной датой без фиксированной длины. С http://www.gnu.org/software/tar/manual/html_node/Relative-items-in-date-strings.html#SEC120

Единицу смещения времени можно выбрать по строке «год» или «месяц» для перемещения целыми годами или месяцами. Это нечеткие единицы, поскольку годы и месяцы не одинаковы. Более точные единицы – «две недели», стоимость которых составляет 14 дней, «неделя» – 7 дней, «день» – 24 часа, «час» – 60 минут, минута или минута 60 секунд, вторая – 'sec' стоит одна секунда. Суффикс 's' на этих устройствах принимается и игнорируется.

Следовательно (акцент мой)

Fuzz в единицах может вызвать проблемы с относительными элементами. Например, «2003-07-31 -1 месяц» может оцениваться до 2003-07-01, поскольку 2003-06-31 является недопустимой датой. Чтобы более надежно определить предыдущий месяц, вы можете запросить месяц до 15 числа текущего месяца . Например:

 $ date -R Thu, 31 Jul 2003 13:02:39 -0700 $ date --date='-1 month' +'Last month was %B?' Last month was July? $ date --date="$(date +%Y-%m-15) -1 month" +'Last month was %B!' Last month was June! 

Вышеприведенное может быть выражено в PHP как

 echo date('M', strtotime(date('Ym-') . '15 -1 month')); 

Также см. Сообщения ниже http://bugs.php.net/bug.php?id=22486

Из PHP 5.3 (ссылка: https://bugs.php.net/bug.php?id=44073 ) и выше вы можете сделать:

« first day of +1 month » или « first day of next month » или даже « last day of next month »,

Пример:

 $date = '2015-12-31'; echo date("Ymd", strtotime($date ."first day of previous month")); 

Будет производить: 2015-11-01 Это не рассчитывает дни на +30 дней.

простой способ мог бы написать его вот так:

echo date («M», strtotime («в этом году +3 месяца»));

или

echo date («M», strtotime («в этом месяце -3 месяца»));

зависит от того, что вы используете для ..