明日の日付や1週間後の日付、一時間後の時間などの日時の加算や、昨日の日付や昨年の日付などの日時の減算の方法をご紹介します。
strtotime()とDateTimeクラスでのやり方をそれぞれ見ていきましょう。
先月の日付を取得する際は、月末日の関係でおかしな日付になることもあるため、その解決法にも触れています。
目次
strtotime関数での加算、減算
※以下は今日が2016-1-29の場合
明日の日付を表示
|
1 2 3 |
echo date('Y-m-d', strtotime('+1 day')); // 2016-01-30 echo date('Y-m-d', strtotime('tomorrow')); // 2016-01-30 |
どちらも明日の日付が表示されます。
+1 daytomorrowどちらでも明日の日付が取得できますね。
1年後の日付を取得
|
1 |
echo date('Y年m月d日', strtotime('+1 year')); // 2017年01月29日 |
ちょうど1年後の日付が取得できました。
ついでに、フォーマットも「年月日」にして表示させています。
所定の日付の翌日を表示
|
1 2 3 |
echo date('Y-m-d', strtotime('2015-12-31 +1 day')); // 2016-01-01 echo date('Y-m-d', strtotime('2015-12-31 tomorrow')); // 2016-01-01 |
strtotime()に所定の日付を入れ、半角スペースで繋ぎました。
2015-12-31の翌日、つまり2016-01-01の日付が取得できています。
1時間後の時間を表示
※以下は現在の時刻が21:49の場合
|
1 |
echo date('H:i', strtotime('+1 hour')); // 22:49 |
昨日の日付を表示
|
1 2 3 |
echo date('Y-m-d', strtotime('-1 day')); // 2016-01-28 echo date('Y-m-d', strtotime('yesterday'));// 2016-01-28 |
昨日や昨年、先月などの減算もできますよ。
strtotime関数のフォーマット一覧
以下のようなフォーマットを使って日付の加算、減算ができます。
| フォーマット | 説明 | サンプル |
|---|---|---|
| now | 現在の日時を取得 | 2016/01/29 21:49:15 |
| tomorrow | 明日の日付を取得 | 2016/01/30 21:49:15 |
| yesterday | 昨日の日付を取得 | 2016/01/28 21:49:15 |
| +1 day | 1日後の日時を取得 | 2016/01/30 21:49:15 |
| +1 week | 1週間後の日時を取得 | 2016/02/05 21:49:15 |
| +1 month | 1ヶ月後の日時を取得 | 2016/02/29 21:49:15 |
| +1 year | 1年後の日時を取得 | 2016/03/01 21:49:15 |
| +1 hour | 1時間後の日時を取得 | 2016/01/30 22:49:15 |
| +1 minute | 1分後の日時を取得 | 2016/01/30 21:50:15 |
| +1 second | 1秒後の日時を取得 | 2016/01/30 21:49:16 |
| last day of previous month | 先月の末日を取得 | 2015/12/31 |
ただstrtotime()は2038年問題などもあり、DateTimeクラスを使うように推奨されることも多いようです。
次は、DateTimeクラスで同じことをやってみましょう。
DateTimeクラスで加算、減算
※以下は現在が2016-1-29 21:49の場合
modifyを使う
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
$date = new DateTime(); // 明日の日付 echo $date->modify('+1 day')->format('Y-m-d'); // 2016-01-30 echo $date->modify('tomorrow')->format('Y-m-d'); // 2016-01-30 // 1年後の日付 echo $date->modify('+1 year')->format('Y-m-d'); // 2017-01-30 // 1時間後の時間 echo $date->modify('+1 hour')->format('H:i'); // 22:49 // 昨日の日付 echo $date->modify('-1 day')->format('Y-m-d'); // 2016-01-28 echo $date->modify('yesterday')->format('Y-m-d'); // 2016-01-28 |
説明
DateTimeクラスでmodifyを使った日付の加算、減算は以下のようになっています。
$date = new DateTime();
- まず
new DateTime();でDateTimeオブジェクトを作る - そしてそのオブジェクトを変数
$dateに格納
echo $date->modify(相対的な書式)->format(出力フォーマット);
- 変数
$dateをmodifyで加算、減算の相対的な書式で指定した日付に移動させる(tomorrow+1 day…など) - その日付を
formatで指定した書式で表示させる
変数$dateはオブジェクト型で、日時やタイムゾーンが格納されています。
そこから日付を->modifyで加算、減算させて、さらに->formatでY-m-dの書式でフォーマットして表示しているんですね。
先月の日付を取得する際は要注意!
日付の加算、減算で先月の日付を取得する場合の注意点です。
まずは下記サンプルをご覧ください。
先月の日付を取得
|
1 |
echo date('Y-m-d', strtotime('-1 month')); // 2015-12-29 |
上記は問題なく1ヶ月前の日付が取れていますね。
それでは3/31の1ヶ月前だとどうなるでしょうか?
月によって末日が違うことで起きる弊害
|
1 |
echo date('Y-m-d', strtotime('2016-3-31 -1 month')); // 2016-03-02 |
3/31の1ヶ月前が3/2と出力されます。これは問題ですね!
理屈は以下のとおりです。
- 3/31の
-1 monthは2/31と判定 - しかし2/31なんて日付はないから、実際に存在する2/29の次から2つ余った分を3月に自動的に変換してしまう(この年はうるう年ですw)
- そのまま
3/2と表示された
月の加算、減算の場合のみ、1ヶ月前の日と、その月の末日と比較してちょっと一工夫する必要があります。
次の項目で、月の加算、減算の簡単なプログラムを作ってみました。
先月の日付を正確に表示させるプログラム
|
1 2 3 4 5 6 7 8 9 10 |
$date = strtotime('2016-3-31'); // 2016-03-31 $lastDay = date('Y-m-d', strtotime('last day of previous month', $date)); //2016-02-29 $prev = date('Y-m-d', strtotime('-1 month', $date)); //2016-03-02 if ($lastDay < $prev) { echo $lastDay; } else { echo $prev; } |
2016-02-29
3/31の1ヶ月前でもきちんと2月の末日の2/29と表示されました。
このプログラムの概要は以下のとおりです。
- 変数
$dateに所定の日付を格納 - 変数
$lastDayに先月末日を取得するコードを格納 - 変数
$prevに-1 monthした時の日付を格納 - if文で先月の末日と、日付を
-1 monthして取得した日付を比較 - もし、日付を
-1 monthして取得した日付の方が大きければ、先月末日を表示 - もし、先月末日と同じか、それよりも小さい日付ならば、日付を
-1 monthして取得した日付を表示
ポイントは、2.のstrtotime()に設定したlast day of previous monthですね。
「前の月の最後の日」と直訳できるかと思いますが、先月の末日を取得するフォーマットです。
これで、簡単に先月末の正確な日付を取得できますね。
DateTimeクラスでも同じようにやってみましょう。
