如何在Laravel和PHP中使用Carbon管理DateTime

来自菜鸟教程
跳转至:导航、​搜索

介绍

在 PHP 中处理日期和时间可能很复杂。 我们必须处理 strtotime、格式问题、大量计算等等。

Carbon 包可以帮助在 PHP 中处理日期和时间变得更加容易和语义化,从而使我们的代码变得更具可读性和可维护性。

Carbon 是 Brian Nesbit 的一个包,它扩展了 PHP 自己的 DateTime 类。

它提供了一些很好的功能来处理 PHP 中的日期。 具体如下:

  • 处理时区。
  • 轻松获取当前时间。
  • 将日期时间转换为可读的东西。
  • 将英文短语解析为日期时间 ("first day of January 2016")。
  • 加减日期("+ 2 weeks""-6 months")。
  • 处理日期的语义方式。

在本文中,您将安装 Carbon 并探索它提供的特性和功能。

先决条件

要遵循本指南,您需要满足以下先决条件:

  • 一个工作的 Laravel 开发环境。 要进行设置,您可以按照我们关于 如何在 Ubuntu 20.04 上安装和配置 Laravel 应用程序的指南进行操作。 或者,按照 Larvel 安装文档进行操作。 如果你选择 Laravel Sail 方法,你将需要 Docker。

本教程已使用 PHP v8.0.5、Composer v2.0.13、MySQL 8.0.24、Laravel v8.40.0 和 Carbon v2.31 进行了验证。

设置项目

为了使用 Carbon,您需要从 Carbon 命名空间导入 Carbon。 幸运的是,Carbon 已经包含在 Laravel 中。

每当我们需要使用 Carbon 时,我们可以像这样导入它:

<?php
use Carbon\Carbon;

导入之后,我们来探索一下 Carbon 提供了什么。

获取特定日期和时间

获取当前时间:

$current = Carbon::now();

当前时间也可以用这个实例化来检索:

$current2 = new Carbon();

获取今天的日期:

$today = Carbon::today();

获取昨天的日期:

$yesterday = Carbon::yesterday();

获取明天的日期:

$tomorrow = Carbon::tomorrow();

解析一个特定的字符串:

$newYear = new Carbon('first day of January 2016');

这将返回:

Output2016-01-01 00:00:00

这些助手为频繁的日期和时间需求提供人类可读的请求,例如 today()yesterday()tomorrow()

创建具有更细粒度控制的日期

除了定义日期和时间的快速方法之外,Carbon 还让我们根据特定数量的参数创建日期和时间。

createFromDate() 接受 $year$month$day$tz(时区):

Carbon::createFromDate($year, $month, $day, $tz);

createFromTime() 接受 $hour$minute$second$tz(时区):

Carbon::createFromTime($hour, $minute, $second, $tz);

create() 接受 $year$month$day$hour$minute$second、[ X84X](时区):

Carbon::create($year, $month, $day, $hour, $minute, $second, $tz);

当您以 Carbon 通常无法识别的格式获取某种日期或时间时,这些非常有用。 如果您为这些属性中的任何一个传入 null,它将默认为当前。

操作日期和时间

在处理日期时,获取日期和时间并不是您唯一需要做的事情。 您经常需要操纵日期或时间。

例如,在为用户创建试用期时,您会希望试用期在一定时间后到期。 假设我们有 30 天的试用期。 我们可以用 Carbon 的 addsubtract 来计算时间。

对于此示例,我们可以使用 addDays() 来确定试用期何时到期:

// get the current time
$current = Carbon::now();

// add 30 days to the current time
$trialExpires = $current->addDays(30);

来自 Carbon 文档,这里有一些可供我们使用的其他 add()sub() 方法。

考虑一个设置为 2012 年 1 月 31 日的日期:

$dt = Carbon::create(2012, 1, 31, 0);

echo $dt->toDateTimeString();

这将返回:

Output2012-01-31 00:00:00

使用 addYears()subYears() 修改日期将导致以下结果:

命令 输出
echo $dt->addYear(); 2012-01-31 00:00:00
echo $dt->addYears(5); 2017-01-31 00:00:00
echo $dt->subYear(); 2011-01-31 00:00:00
echo $dt->subYears(5); 2007-01-31 00:00:00

使用 addMonths()subMonths() 修改日期将导致以下结果:

命令 输出
echo $dt->addMonth(); 2012-03-03 00:00:00
echo $dt->addMonths(60); 2017-01-31 00:00:00
echo $dt->subMonth(); 2011-12-31 00:00:00
echo $dt->subMonths(60); 2007-01-31 00:00:00

请注意在“1 月 31 日”中添加一个月如何导致“3 月 3 日”而不是“2 月 28 日”。 如果您不想进行翻转,可以使用 addMonthWithoutOverflow()

使用 addDays()subDays() 修改日期将导致以下结果:

命令 输出
echo $dt->addDay(); 2012-02-01 00:00:00
echo $dt->addDays(29); 2012-02-29 00:00:00
echo $dt->subDay(); 2012-01-30 00:00:00
echo $dt->subDays(29); 2012-01-02 00:00:00

使用 addWeekdays()subWeekdays() 修改日期将导致以下结果:

命令 输出
echo $dt->addWeekday(); 2012-02-01 00:00:00
echo $dt->addWeekdays(4); 2012-02-06 00:00:00
echo $dt->subWeekday(); 2012-01-30 00:00:00
echo $dt->subWeekdays(4); 2012-01-25 00:00:00

使用 addWeeks()subWeeks() 修改日期将导致以下结果:

命令 输出
echo $dt->addWeek(); 2012-02-07 00:00:00
echo $dt->addWeeks(3); 2012-02-21 00:00:00
echo $dt->subWeek(); 2012-01-24 00:00:00
echo $dt->subWeeks(3); 2012-01-10 00:00:00

使用 addHours()subHours() 修改日期将导致以下结果:

命令 输出
echo $dt->addHour(); 2012-01-31 01:00:00
echo $dt->addHours(24); 2012-02-01 00:00:00
echo $dt->subHour(); 2012-01-30 23:00:00
echo $dt->subHours(24); 2012-01-30 00:00:00

使用 addMinutes()subMinutes() 修改日期将导致以下结果:

命令 输出
echo $dt->addMinute(); 2012-01-31 00:01:00
echo $dt->addMinutes(61); 2012-01-31 01:01:00
echo $dt->subMinute(); 2012-01-30 23:59:00
echo $dt->subMinutes(61); 2012-01-30 22:59:00

使用 addSeconds()subSeconds() 修改日期将导致以下结果:

命令 输出
echo $dt->addSecond(); 2012-01-31 00:00:01
echo $dt->addSeconds(61); 2012-01-31 00:01:01
echo $dt->subSecond(); 2012-01-30 23:59:59
echo $dt->subSeconds(61); 2012-01-30 23:58:59

使用 Carbon 的 addsubtract 工具可以为您提供调整后的日期和时间。

使用 Getter 和 Setter

另一种读取或操作时间的方法是使用 Carbon 的 getter 和 setter。

使用 getter 读取值:

$dt = Carbon::now();

var_dump($dt->year);
var_dump($dt->month);
var_dump($dt->day);
var_dump($dt->hour);
var_dump($dt->second);
var_dump($dt->dayOfWeek);
var_dump($dt->dayOfYear);
var_dump($dt->weekOfMonth);
var_dump($dt->daysInMonth);

使用设置器更改值:

$dt = Carbon::now();

$dt->year   = 2015;
$dt->month  = 04;
$dt->day    = 21;
$dt->hour   = 22;
$dt->minute = 32;
$dt->second = 5;

echo $dt;

我们甚至可以将一些二传手链接在一起。

这是前面使用 year()month()day()hour()minute()second() 的示例:

$dt->year(2015)->month(4)->day(21)->hour(22)->minute(32)->second(5)->toDateTimeString();

这是使用 setDate()setTime() 的相同示例:

$dt->setDate(2015, 4, 21)->setTime(22, 32, 5)->toDateTimeString();

这是使用 setDateTime() 的相同示例:

$dt->setDateTime(2015, 4, 21, 22, 32, 5)->toDateTimeString();

所有这些方法都会产生相同的结果:2015-04-21 22:32:05

格式化日期和时间

PHP 的 toXXXString() 方法可用于以预定义格式显示日期和时间:

命令 输出
echo $dt->toDateString(); 2015-04-21
echo $dt->toFormattedDateString(); 2015 年 4 月 21 日
echo $dt->toTimeString(); 22:32:05
echo $dt->toDateTimeString(); 2015-04-21 22:32:05
echo $dt->toDayDateTimeString(); 2015 年 4 月 21 日星期二晚上 10:32

也可以使用 PHP 的 DateTime format() 进行自定义格式:

echo $dt->format('l jS \of F Y h:i:s A');
  • l:星期几的完整文本表示。
  • jS : 没有前导零的月份中的某天。 日期的英文序号后缀,2 个字符。
  • F:一个月的完整文本表示。
  • Y:年份的完整数字表示,4 位数字。
  • h:i:s : 带前导零的小时的 12 小时格式。 带前导零的分钟。 带前导零的秒数。
  • A:大写的 Ante meridiem 和 Post meridiem。

此代码将产生以下结果:

OutputTuesday 21st of April 2015 10:32:05 PM

使用 Carbon 的格式化工具可以显示日期和时间以满足您的需求。

计算相对时间

Carbon 还允许我们使用 diff() 方法相对显示时间。

例如,假设我们有一个博客,想要显示 3 hours ago 的发布时间。 我们可以用这些方法做到这一点。

寻找差异

考虑以下示例,其中包含未来时间和过去时间:

$dt      = Carbon::create(2012, 1, 31, 0);
$future  = Carbon::create(2012, 1, 31, 0);
$past    = Carbon::create(2012, 1, 31, 0);

$future  = $future->addHours(6);
$past    = $past->subHours(6);

以下是使用 diffInHours() 的结果:

命令 输出
echo $dt->diffInHours($future); 6
echo $dt->diffInHours($past); 6

考虑以下示例,其中包含未来的日期和过去的日期:

$dt      = Carbon::create(2012, 1, 31, 0);
$future  = Carbon::create(2012, 1, 31, 0);
$past    = Carbon::create(2012, 1, 31, 0);

$future  = $future->addMonth();
$past    = $past->subMonths(2);

以下是使用 diffInDays() 的结果:

命令 输出
echo $dt->diffInDays($future); 31
echo $dt->diffInDays($past); 61

显示人类的差异

相对显示时间有时对读者来说比日期或时间戳更有用。

例如,不会像 8:12 AM 那样显示帖子的时间,而是将时间显示为 3 hours ago

diffForHumans() 方法用于计算差异并将其转换为人类可读的格式。

考虑以下示例,其中包含未来的日期和过去的日期:

$dt      = Carbon::create(2012, 1, 31, 0);
$future  = Carbon::create(2012, 1, 31, 0);
$past    = Carbon::create(2012, 1, 31, 0);

$future  = $future->addMonth();
$past    = $past->subMonth();

以下是使用 diffForHumans() 的结果:

命令 输出
echo $dt->diffForHumans($future); 1 month before
echo $dt->diffForHumans($past); 1 month after

结论

在本文中,您安装了 Carbon 并探索了它提供的特性和功能。

如果您想了解有关 Laravel 的更多信息,请查看 我们的 Laravel 主题页面 以获取练习和编程项目。 如果您想了解有关 PHP 的更多信息,请查看 我们的 PHP 主题页面 以获取练习和编程项目。