PHP 怎么PHP 8.3 常量类型

wen PHP项目 2

本文目录导读:

PHP 怎么PHP 8.3 常量类型

  1. 核心语法
  2. 重点说明
  3. 代码示例
  4. 与 PHP 8.2 及之前的区别
  5. 实际开发建议

在 PHP 8.3 中,常量类型(Typed Constants) 是一个重要的新特性,它允许你在定义类常量、接口常量、trait 常量以及全局常量(define() 函数)时,显式声明常量的数据类型。

核心语法

// 类常量(最常用)
class MyClass {
    public const int MAX_ITEMS = 100;
    public const string APP_NAME = 'MyApp';
}
// 接口常量
interface MyInterface {
    public const string INTERFACE_NAME = 'MyInterface';
}
// trait 常量
trait MyTrait {
    public const float PI = 3.14159;
}
// 全局常量(使用 define)
define('int', 100);
// 注意:全局常量使用 define() 时,类型声明放在第二个参数后面(不太自然)
define(constant_name: 'SITE_URL', value: 'https://example.com');
// PHP 8.3 的 define() 本身不支持直接写类型,上面的写法有问题。
// 正确写法(PHP 8.3 允许常量类型用于 define,但语法是新的)
define('int', 100); // 这仍然是旧语法,没有类型。
// PHP 8.3 中 define() 支持类型? PHP 8.3 并没有为 define() 添加类型声明。
// 所以以上是错误的,正确的全局常量类型声明只能用于类常量。
// 重新说明:
// 实际支持的写法(仅在类、接口、trait 内):
class MyClass {
    public const int MAX = 100; // 正确
    // public const string? NAME = null; // 不允许 nullable(联合类型也不行?暂时不行)
    // public const int|string ID = 123; // 不允许联合类型(仅基本类型 + readonly?)
}

重点说明

  1. 支持的类型:PHP 8.3 常量类型支持的标量类型包括:

    • bool
    • int
    • float
    • string
    • array(必须为常量数组字面量)
    • null(PHP 8.3 允许 null 作为类型,但常量必须为 null,如果声明 null 类型则只能赋值 null
  2. 不支持的类型

    • voidnevercallable(因为常量不能是函数或可调用对象)
    • object(常量不能是对象实例)
    • 联合类型(int|string 不允许)
    • 交集类型(A&B 不允许)
    • 可空类型(?int 不允许,但可以用 int|null?也不行,因为联合类型不支持)
    • mixed 不支持
  3. 强制执行:如果赋值的常量值与声明的类型不匹配,PHP 8.3 会抛出 TypeError 错误(不仅警告)。

    • class Foo {
          public const int VALUE = 'hello'; // TypeError
      }
  4. 继承与覆盖

    如果子类覆盖父类的常量,子类常量的类型必须与父类兼容(或相同),如果能不写类型,则允许不写;如果写了,必须兼容。

代码示例

<?php
class Configuration {
    // 标量类型
    public const bool DEBUG = true;
    public const int MAX_RETRIES = 3;
    public const float TIMEOUT = 30.5;
    public const string APP_NAME = 'MyApp';
    public const array COLORS = ['red', 'green', 'blue'];
    // 允许 final 修饰符(已有)
    final public const string VERSION = '1.0';
}
// 错误用法
// class BadClass {
//     public const int VALUE = 'not int'; // TypeError
// }
// 可空 null 类型
class NullableConst {
    public const null NULL_CONST = null; // 只能赋值 null
    // public const null INVALID = 1; // 会报 TypeError
}
echo Configuration::DEBUG; // 输出 true
echo Configuration::MAX_RETRIES; // 3

与 PHP 8.2 及之前的区别

特性 PHP 8.2 及之前 PHP 8.3
类常量类型声明 不支持(只能通过 PHPDoc 暗示) 支持(语法错误级)
类型检查 无静态检查(运行时弱类型转换) 严格类型检查(抛出 TypeError)
定义语法 const VALUE = 42; const int VALUE = 42;

实际开发建议

  • 类常量:推荐在需要确保常量类型一致时(如配置项、枚举类)使用类型声明,提高代码健壮性。
  • 全局常量define()):PHP 8.3 没有define() 添加类型声明,仅在类/接口/trait 内有效。
  • final 结合:可以同时使用 finalconst 防止子类覆盖,final public const int SIZE = 10;
  • 向后兼容:旧代码无需修改,未加类型声明的常量行为不变(仍然会自动类型转换,如 const A = '1' 但实际赋值给 int 上下文时不会报错,因为没声明类型)。

PHP 8.3 的常量类型是一个实用的类型安全增强,尤其适合接口、配置类、枚举(配合 final)等场景,虽然目前支持的类型有限(仅标量 + null + array),但它为未来的 PHP 版本打下了更好基础,建议你在新项目中使用,并配合 IDE 的类型检查,可以早期发现潜在的常量赋值错误。

抱歉,评论功能暂时关闭!