Точный способ добавить месяцы в PHP 5.1? - PullRequest
7 голосов
/ 02 июня 2011

Вчера я столкнулся с проблемой, связанной с неправильным добавлением месяца в strtotime PHP. «2011-05-31» я пробежал:

date('Y-m-d',strtotime( '+1 month', strtotime('now')));

Что возвращает «2011-07-01», когда я ожидаю «2011-06-30».

У MySQL нет проблем с этим.

Я бы предпочел не изобретать велосипед с этим, так как довольно легко допустить ошибки с расчетами даты из моего опыта.

У кого-нибудь есть надежное и проверенное решение для этого для PHP 5.1?

Ответы [ 7 ]

5 голосов
/ 02 июня 2011

Это, конечно, возможно в PHP: проверьте руководство strtotime, особенно этот комментарий .

Если у вас есть доступное соединение MySQL, SELECT DATE_ADD( '2011-05-31', INTERVAL 1 MONTH ) будет менее избыточным, так как (правильная) функциональность уже реализована без необходимости его самостоятельной реализации.

2 голосов
/ 02 июня 2011

Поскольку эта тема кажется довольно запутанной, вот некоторая информация по ней:

Вы на самом деле получаете точный результат, буквально увеличивая месяц на 1, день остается 31, поэтому дата 2011-06-31. Если вы сделаете echo date('Y-m-d', strtotime('2011-06-31'));, вы увидите, что отображается 2011-07-01.

Вот один из способов сделать эту работу "ожидаемой" в PHP 5.1 (и ранее)

function next_month($timestamp)
{
    $next_month = date('m', $timestamp);
    $next_month++;

    $next_year = date('Y', $timestamp);

    if($next_month == 12)
    {
        $next_year++;
    }

    if(date('d', $timestamp) <= date('t', mktime(0, 0, 0, $next_month, 1, $next_year)))
    {
        return date('Y-m-d',strtotime( '+1 month', $timestamp));
    }
    else
    {
        return date('Y-m-d', mktime(0, 0, 0, $next_month, date('t', mktime(0, 0, 0, $next_month, 1, $next_year)), $next_year));
    }
}

echo next_month(strtotime('2011-05-31'));

echo next_month(strtotime('2011-05-01'));

Это модифицированный код из библиотеки, которую я написал недавно - я никогда не находил элегантного решения.

Для PHP 5.3 +

См. PHP DateTime :: изменение сложения и вычитания месяцев для подробных вопросов и ответов по этой теме.

1 голос
/ 16 мая 2018

Попробуйте использовать:

$date = date_create("1900-01-01"); // Your start date
$new_date = date_add($date, date_interval_create_from_date_string('1 month')); // Your end date
1 голос
/ 02 июня 2011

Вы можете сравнить результат strtotime( 'last day of +1 month', strtotime('now')) с strtotime( '+1 month', strtotime('now')) и использовать тот, который раньше.

1 голос
/ 02 июня 2011

Добавление +2592000 seconds ( 60 × 60 × 24 × 30 ) работает для меня желаемым образом.

1 голос
/ 02 июня 2011

Можно утверждать, что PHP работает правильно, а MySQL - неправильно:

MySQL ограничивает значение до последней действительной даты, которая соответствует определению года / месяца. PHP корректируется вверх, двигаясь вперед к первой правильной дате, которая соответствует указанному дню (31-30 = 1 день назад, поэтому 2011-06-30 + 1 день = 2011-07-01).

0 голосов
/ 06 мая 2015
For other Months : date('Y-m-t',strtotime("2015-05-31T23:59:59 -3 days +1 month"));
Output           : 2015-06-30

For Feb          : date('Y-m-t',strtotime("2015-01-31T23:59:59 -3 days +1 month"));
Output           : 2015-02-28

Это решит вашу проблему.

...