PHPのstrtotime()では2017-03-31の1ヶ月後は「2017-04-31」となり、
「2017-04-31」は「2017-05-01」として解釈される
例)以下のように月が重複して作成される
<?php
// 現在の日付から半年間の月のリストを作成する
$target_date = "20170331";
for ($i=0; $i < 6; $i++) {
$target_ym_list[] = date('Ym', strtotime($target_date . '+' . $i . ' month'));
}
var_dump($target_ym_list);
?>
array(6) {
[0]=>
string(6) "201703"
[1]=>
string(6) "201705"
[2]=>
string(6) "201705"
[3]=>
string(6) "201707"
[4]=>
string(6) "201707"
[5]=>
string(6) "201708"
}
昔から現場ではよく問題となっていましたが、今だ撲滅はされていません。
(「PHP 1か月前」とかでググると以下のようなソースが簡単に見つかるため)
<?php
// 1ヶ月後の日時を取得
echo date("Y-m-d",strtotime($target_day . "+1 month"));
?>
解決方法としては、以下のように指定日時を月はじめに変換するとよい。
<?php
// 現在の日付から半年間の月のリストを作成する
$target_date = "20170331";
// 指定日時を月はじめに変換する
$target_date = date("Ym01", strtotime($target_date));
for ($i=0; $i < 6; $i++) {
$target_ym_list[] = date('Ym', strtotime($target_date . '+' . $i . ' month'));
}
var_dump($target_ym_list);
?>
array(6) {
[0]=>
string(6) "201703"
[1]=>
string(6) "201704"
[2]=>
string(6) "201705"
[3]=>
string(6) "201706"
[4]=>
string(6) "201707"
[5]=>
string(6) "201708"
}