PHP中的日期与时间操作

官方文档学习笔记

PHP 官方文档中 《Function Reference - Date and Time Related Extensions》 这个章节,包含三个小节,分别为 Calendar,Date/Time, HRTime。

其中《Date/Time》一节,讲述了常见的日期与时间操作的方法。主要包括一个接口,五个类(两个大类,三个小类),一系列类的「实例方法」的别名:

  • DateTimeInterface,一个接口。

  • DateTime,一个类。实现了上述 DateTimeInterface 接口。表示「日期和时间」的类。

  • DateTimeImmutable,一个类。此类的行为与 DateTime 类相同,可以理解成是同一个类。不同之处在于 DateTime 类的实例调用某些方法时,实例本身会被修改。而 DateTimeImmutable 类的实例则不会。

  • DateInterval,一个类。表示「时间间隔」的类。

  • DateTimeZone,一个类。表示「时区」的类。

  • DatePeriod,一个类。表示「时间周期」的类。实现了 IteratorAggregate 接口。

  • Date/Time Functions,主要讲述的是一些与时间日期操作相关的函数,这些函数大多是 DateTime 类和 DateTimeImmutable 类的「实例方法」的别名。

DateTime 与 DateTimeImmutable 这两个类的区别

可以理解成是同一个类,唯一的区别是,DateTime 类的实例调用某些方法时会修改自身的值,而 DateTimeImmutable 类的实例则不会。

关于 DateInterval 类

DateInterval 简介

英语单词 Interval 即间隔的意思。
DateInterval 类的实例表示两个日期之间的间隔。
DateTime() 或 DateTimeImmutable 对象调用 diff() 方法时会返回一个 DateInterval 类的实例。
可以将 DateInterval 类的实例传递给 DateTime 或 DateTimeImmutable 类的实例的add()方法或sub()方法,从而实现日期的加减。

如何创建 DateInterval 实例

可以通过以下方式创建一个 DateInterval 实例:


// -----------------------------------------------------------------------------
// 方式一 面向对象
// -----------------------------------------------------------------------------

// 间隔1天
$intervalOne = new DateInterval("P1D");
echo "间隔" . $intervalOne->format("%d") . "天";

// 间隔1天零1小时
$intervalTwo = new DateInterval("P1DT3H");
echo "间隔" . $intervalTwo->format("%d天%h小时");

// -----------------------------------------------------------------------------
// 方式二 面向对象
// -----------------------------------------------------------------------------
// 与方式三类似

// 1 day 可以, One day 则会报错。
$intervalOne = DateInterval::createFromDateString("1 day");
$intervalTwo = DateInterval::createFromDateString("2 weeks");

// -----------------------------------------------------------------------------
// 方式三 面向过程
// -----------------------------------------------------------------------------

$intervalOne = date_interval_create_from_date_string("1 day");

// hour 或者 hours 都可以,不必纠结
$intervalTwo = date_interval_create_from_date_string("1 day + 1 hour");


创建 DateInterval 时,参数中的 P1DT3H 的意思

官方文档中的解释是:
The format starts with the letter P, for period. Each duration period is represented by an integer value followed by a period designator. If the duration contains time elements, that portion of the specification is preceded by the letter T.

大意是「间隔」都要以字母P开头,后面接天数,1Y是1年,1M是1月,1D是1天,1W是1周,1H是1时,1M是1分,1S是1秒。

需要特别注意的是,如果间隔具体到几个小时几分几秒,则要在具体的时间前加上一个字母T。比如:

  • P1D ,间隔1天。
  • P1DT1H,间隔1天零1小时。
  • PT1H ,间隔1小时。即使前面没有天数,字母P也是必不可少的。

详情参考:https://www.php.net/manual/en/dateinterval.construct.php

常见的时间日期操作相关的函数

time()

返回当前时间的时间戳。返回的时间戳形如「1707842721」。
配合 data() 函数可以打印人类容易理解的时间。

date()

格式化打印时间戳。

这个函数接收两个参数。
第一个参数是一个字符串,指定将以哪种格式打印日期。常用的格式有「Ymd」,「Y-m-d」。
第二个参数是一个时间戳,指定要格式化显示的具体时间。这第二个参数是可选的,如用户没有指定,其默认值为 time() 的值。

strtotime()

将「表示时间的英文字符串」转换成「时间戳」。

date_create()

创建一个 DateTime 对象。

date_diff()

计算两个日期的间隔。

date_add()

计算n天后的日期。

date_sub()

计算n天前的日期。

常见的日期与时间操作

格式化打印指定日期

在下面的示例中,DateTimeInterface::format() 中的Y表示年,m表示月,d表示日。
要查看更多关于DateTimeInterface::format()的信息,参考:
https://www.php.net/manual/en/datetime.format.php

<?php

// -----------------------------------------------------------------------------
// 方式一 面向对象
// -----------------------------------------------------------------------------

// 今天
$today = new DateTime("today");
$today = $today->format("Ymd");

// 某天
$someday = new DateTime("20240214");
$someday = $someday->format("Y-m-d");

// -----------------------------------------------------------------------------
// 方式二 面向过程
// -----------------------------------------------------------------------------

// 今天
$today = date("Ymd");
// $today = date("Ymd", time());
//$today = date("Ymd", strtotime("today"));

// 某天
$someDay = date("Ymd", strtotime("2024-02-14"));

// -----------------------------------------------------------------------------

计算两个日期的间隔

在下面的示例中,DateInterval::format() 方法中的 %R 表示间隔天数的正负符号,%a 表示总间隔天数。
要查看更多关于 DateInterval::format() 的信息,参考:
https://www.php.net/manual/en/dateinterval.format.php

<?php

// -----------------------------------------------------------------------------
// 方式一 面向对象
// -----------------------------------------------------------------------------

// 把下面的 DateTime() 换成 DateTimeImmutable(),效果是一样的。

$origin = new DateTime("yesterday"); // 返回 DateTime 对象
$target = new DateTime("tomorrow");  // 返回 DateTime 对象
$interval = $origin->diff($target);  // 返回 DateInterval 对象
echo $interval->format('%R%a 天');   // 返回字符串

// -----------------------------------------------------------------------------
// 方式二 面向过程
// -----------------------------------------------------------------------------

// 不同于 date_add() 或 date_sub(),date_diff() 函数可以接收 DateTimeImmutable 对象。
// 可以通过 date_create_immutable() 函数创建 DateTimeImmutable 对象。

$origin = date_create('2009-10-11');     // 返回 DateTime 对象
$target = date_create('2009-10-13');     // 返回 DateTime 对象
$interval = date_diff($origin, $target); // 返回 DateInterval 对象
echo $interval->format('%R%a days');     // 返回字符串

// -----------------------------------------------------------------------------

计算n天前与n天后的日期


// -----------------------------------------------------------------------------
// 方式一 面向对象 DateTimeImmutable
// -----------------------------------------------------------------------------
// 推荐使用这种方式

$today = new DateTimeImmutable("today"); // 返回 DateTimeImmutable 对象
$interval = new DateInterval("P2D");     // 返回 DateInterval 对象
// add() 增加,sub() 减少
$targetday = $today->add($interval);     // 返回 DateTimeImmutable 对象
echo $targetday->format("Ymd");
echo "<br />";
echo $today->format("Ymd"); // 注意这里,调用 add() 方法后,$today 的值并没有改变

// -----------------------------------------------------------------------------
// 方式二 面向对象 DateTime
// -----------------------------------------------------------------------------
// 推荐使用方式一

// DateTime 类的实例,调用某些方法后,实例本身会被修改。

$today = new DateTime("today");
$interval = new DateInterval("P2D");
// add() 增加,sub() 减少
$targetday = $today->add($interval);
echo $targetday->format("Ymd");
echo "<br />";
echo $today->format("Ymd"); // 注意这里,调用 add() 方法后,$today 的值改变了。

// -----------------------------------------------------------------------------
// 方式三 面向过程
// -----------------------------------------------------------------------------
// 推荐使用方式一

// date_add() 加日期
// date_sub() 减日期
// 不同于 date_diff(),date_add() 与 date_sub() 都只能接收 DateTime 对象,
// 不能接收 DateTimeImmutable 对象,
// 强行赋值 DateTimeImmutable 对象会报错。
// 执行日期加减后,DateTime 对象的日期会被修改。

$today = date_create("today"); // 返回 DateTime 对象
$interval = date_interval_create_from_date_string("1 day");
$targetday = date_add($today, $interval);
echo $targetday->format("Ymd");
echo "<br />";
echo $today->format("Ymd"); // 注意这里,执行 date_add() 后,$today 的值改变了。

参考资料

posted @   半山听雨  阅读(219)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· 三行代码完成国际化适配,妙~啊~
· .NET Core 中如何实现缓存的预热?
点击右上角即可分享
微信分享提示