PHP8.1的Enums枚举
PHP 8.1:枚举
它们终于来了——PHP 8.1中将添加对枚举的内置支持!有些人可能认为他们早就应该这样做了,但你没有听到我的抱怨;我很高兴他们做到了!这篇文章致力于深入研究新添加的功能。
像往常一样,在我的 PHP 功能帖子中,我们首先对枚举的外观进行高级概述:
enum Status
{
case DRAFT;
case PUBLISHED;
case ARCHIVED;
}
枚举的好处是它们代表了一组常量值,但最重要的是这些值可以被键入,如下所示:
class BlogPost
{
public function __construct(
public Status $status,
) {}
}
在这个例子中,创建一个枚举并将其传递给 aBlogPost看起来像这样:
$post = new BlogPost(Status::DRAFT);
这就是基础知识,正如您所看到的,它们一点也不复杂。虽然有很多旁注需要做,让我们深入看看枚举!
#枚举方法
枚举可以定义方法,就像类一样。这是一个非常强大的功能,尤其是与match运算符结合使用时:
enum Status
{
case DRAFT;
case PUBLISHED;
case ARCHIVED;
public function color(): string
{
return match($this)
{
Status::DRAFT => 'grey',
Status::PUBLISHED => 'green',
Status::ARCHIVED => 'red',
};
}
}
方法可以像这样使用:
$status = Status::ARCHIVED;
$status->color(); // 'red'
静态方法也是允许的:
enum Status
{
// …
public static function make(): Status
{
// …
}
}
您还可以self在枚举中使用:
enum Status
{
// …
public function color(): string
{
return match($this)
{
self::DRAFT => 'grey',
self::PUBLISHED => 'green',
self::ARCHIVED => 'red',
};
}
}
#枚举接口
枚举可以实现接口,就像普通类一样:
interface HasColor
{
public function color(): string;
}
enum Status implements HasColor
{
case DRAFT;
case PUBLISHED;
case ARCHIVED;
public function color(): string { /* … */ }
}
#枚举值——又名“支持枚举”
枚举值在内部由对象表示,但您可以根据需要为它们赋值;这对于例如很有用。将它们序列化到数据库中。
enum Status: string
{
case DRAFT = 'draft';
case PUBLISHED = 'published';
case ARCHIVED = 'archived';
}
注意枚举定义中的类型声明。它表示所有枚举值都属于给定类型。您也可以将其设为int. 请注意, onlyint和string允许作为枚举值。
enum Status: int
{
case DRAFT = 1;
case PUBLISHED = 2;
case ARCHIVED = 3;
}
类型枚举的技术术语称为“支持枚举”,因为它们由更简单的值“支持”。如果您决定分配枚举值,则所有案例都应该有一个值。你不能混合和匹配它们。没有“支持”的枚举被称为“纯枚举”。
#带接口的支持枚举
如果您将支持的枚举和接口结合使用,则枚举类型必须直接位于枚举名称之后,implements关键字之前。
enum Status: string implements HasColor
{
case DRAFT = 'draft';
case PUBLISHED = 'published';
case ARCHIVED = 'archived';
// …
}
#序列化支持的枚举
如果您要为枚举案例分配值,您可能需要一种方法来序列化和反序列化它们。序列化它们意味着您需要一种访问枚举值的方法。这是通过只读公共属性完成的:
$value = Status::PUBLISHED->value; // 2
可以使用以下方法从值中恢复枚举:Enum::from
$status = Status::from(2); // Status::PUBLISHED
如果传递了未知值tryFrom,还有一个返回null。如果你会使用from会有一个例外。
$status = Status::from('unknown'); // ValueError
$status = Status::tryFrom('unknown'); // null
请注意,您还可以在枚举上使用内置函数serialize和unserialize函数。此外,您可以json_encode与支持的枚举结合使用,其结果将是枚举值。可以通过实现来覆盖此行为JsonSerializable。
#列出枚举值
您可以使用静态方法获取枚举中所有可用案例的列表:Enum::cases()
Status::cases();
/* [
Status::DRAFT,
Status::PUBLISHED,
Status::ARCHIVED
] */
请注意,此数组包含实际的枚举对象:
array_map(
fn(Status $status) => $status->color(),
Status::cases()
);
#枚举是对象
我已经提到枚举值表示为对象,实际上它们是单例对象。这意味着您可以像这样与它们进行比较:
$statusA = Status::PENDING;
$statusB = Status::PENDING;
$statusC = Status::ARCHIVED;
$statusA === $statusB; // true
$statusA === $statusC; // false
$statusC instanceof Status; // true
#枚举作为数组键
由于枚举值实际上是对象,因此目前无法将它们用作数组键。以下将导致错误:
$list = [
Status::DRAFT => 'draft',
// …
];
有一个 RFC来改变这种行为,但它还没有被投票。
这意味着您只能使用枚举作为SplObjectStorage和 中的键WeakMaps。
#性状
枚举可以像类一样使用特征,但有更多限制。不允许覆盖内置的枚举方法,并且它们不能包含类属性 - 枚举中禁止使用这些属性。
#反射和属性
正如预期的那样,添加了一些反射类来处理枚举:ReflectionEnum、ReflectionEnumUnitCase和ReflectionEnumBackedCase。还有一个新enum_exists功能,正如它的名字所暗示的那样。
就像普通的类和属性一样,枚举及其案例可以使用attributes进行注释。请注意,TARGET_CLASS过滤器还将包括枚举。
最后一件事:枚举也有一个只读属性,RFC 提到这是一个实现细节,应该只用于调试目的。不过还是值得一提的。$enum->name
本文出至:学新通
- 版权申明: 本站部分内容来自互联网,仅供学习及演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,请提供相关证据及您的身份证明,我们将在收到邮件后48小时内删除。
- 本站站名: 学新通
- 本文地址: https://www.swvq.com/boutique/detail/1969
- 联系方式: luke.wu@swvq.com
- 来源链接: www.php.cn/topic/php8/484066.html
-
windows上查看nginx是否启动
PHP中文网 04-19 -
2023年最新的28道PHP面试题附答案
PHP中文网 03-27 -
navicat怎样清除注册表
PHP中文网 04-05 -
推荐五款xml编辑工具
PHP中文网 03-04 -
强力推荐10款好看使用的Bootstrap后台管理系统模板
PHP中文网 03-09 -
ChatGPT应用通过Axios+EventSource使用GPT3.5 API
uWydnA 03-13 -
docker hub 进不去怎么办
PHP中文网 03-15 -
vscode怎么调整代码大小两种方法
PHP中文网 03-11 -
navicat连接sqlserver数据库
PHP中文网 04-03 -
navicat删除的数据能还原吗
PHP中文网 04-09