PHP 的 date()(格式化)與 strtotime()(解析英文描述為時間戳)是日期時間處理的黃金搭檔。掌握 strtotime() 豐富的相對時間語法,能用極簡代碼實現複雜的業務日期邏輯。
<?php
date_default_timezone_set('Asia/Shanghai'); // 必須先設置時區
// 基礎模式:date('格式', strtotime('相對描述'))
echo date('Y-m-d', strtotime('yesterday')); // 昨天
echo date('Y-m-d', strtotime('-1 day')); // 昨天(別名)
echo date('Y-m-d', strtotime('+3 days')); // 3 天后
echo date('Y-m-d', strtotime('next Monday')); // 下周一
?>
| 業務需求 | strtotime 參數 | 示例輸出 (2024-01-15 基準) |
|---|---|---|
| 今天 | today / now | 2024-01-15 |
| 昨天 | yesterday / -1 day | 2024-01-14 |
| 明天 | tomorrow / +1 day | 2024-01-16 |
| 前天 | -2 days | 2024-01-13 |
| N 天后 | +N days | +7 days → 2024-01-22 |
| N 天前 | -N days | -30 days → 2023-12-16 |
| 本周一 | this Monday / Monday this week | 2024-01-15 (若今天是周一) |
| 上周一 | last Monday / Monday last week | 2024-01-08 |
| 下周一 | next Monday / Monday next week | 2024-01-22 |
| 本月第一天 | first day of this month | 2024-01-01 |
| 本月最後一天 | last day of this month | 2024-01-31 |
| 上月第一天 | first day of last month | 2023-12-01 |
| 上月最後一天 | last day of last month | 2023-12-31 |
| 下月最後一天 | last day of next month | 2024-02-29 (閏年) |
| 今年第一天 | first day of January this year | 2024-01-01 |
| 去年最後一天 | last day of December last year | 2023-12-31 |
| 具體日期偏移 | 2024-01-15 +2 weeks | 2024-01-29 |
| 下個工作日 | next weekday | 跳過周末 |
<?php
// 錯誤:依賴服務器默認時區(通常是 UTC)
echo date('Y-m-d H:i:s', strtotime('today')); // 可能輸出 2024-01-14 16:00:00
// 正確:入口文件統一設置
date_default_timezone_set('Asia/Shanghai'); // 或 PRC
echo date('Y-m-d H:i:s', strtotime('today')); // 2024-01-15 00:00:00
?>
<?php
// 危險:1月31日 +1 month → 3月3日 (因2月無31日)
echo date('Y-m-d', strtotime('2024-01-31 +1 month')); // 2024-03-02 ❌
// 安全:使用 "first day of next month" 或 "last day of next month"
echo date('Y-m-d', strtotime('first day of next month', strtotime('2024-01-31'))); // 2024-02-01 ✅
echo date('Y-m-d', strtotime('last day of next month', strtotime('2024-01-31'))); // 2024-02-29 ✅
?>
<?php
$base = strtotime('2024-01-15'); // 固定基準
echo date('Y-m-d', strtotime('+1 month', $base)); // 2024-02-15
echo date('Y-m-d', strtotime('last day of this month', $base)); // 2024-01-31
?>
<?php
$inputs = ['2024-01-15', '15/01/2024', 'Jan 15, 2024', '20240115', 'yesterday'];
foreach ($inputs as $input) {
$ts = strtotime($input);
echo $input . ' → ' . ($ts ? date('Y-m-d', $ts) : '解析失敗') . "\n";
}
?>
對於複雜業務、時區轉換、不可變對象需求,推薦使用面向對象的 DateTime / DateTimeImmutable。
<?php
$dt = new DateTime('2024-01-15', new DateTimeZone('Asia/Shanghai'));
$dt->modify('last day of next month');
echo $dt->format('Y-m-d'); // 2024-02-29
// 不可變模式(鏈式調用不修改原對象)
$dtIm = new DateTimeImmutable('2024-01-15');
$nextMonthEnd = $dtIm->modify('last day of next month');
echo $dtIm->format('Y-m-d'); // 2024-01-15 (原對象不變)
echo $nextMonthEnd->format('Y-m-d'); // 2024-02-29
?>
Y 四位年份 2024
m 雙位月份 01
d 雙位日期 15
H 24小時制 14
i 分鐘 30
s 秒 59
w 星期數字 1 (0=周日)
l 星期全稱 Monday
W 年份第幾周 03
t 本月總天數 31
z 年份第幾天 14
c ISO 8601 2024-01-15T14:30:59+08:00
r RFC 2822 Mon, 15 Jan 2024 14:30:59 +0800
結語:strtotime() 的自然語言解析能力極強,配合 date() 格式化,能覆蓋 90% 以上的業務日期計算場景。牢記「先設時區、慎用月份加減、關鍵節點用 first/last day」三大原則,即可寫出健壯、可讀、無 Bug 的日期代碼。