PHP `const`关键字:类常量与常量表达式

PHP const:常量中的战斗机,让你的代码硬邦邦! 💪

各位观众老爷们,大家好!我是你们的老朋友,代码界的段子手,Bug 的终结者——Bug猎手!今天,我们要聊聊 PHP 中一个看似简单,实则蕴含着强大力量的关键字:const

别一听“常量”就觉得枯燥乏味,这玩意儿就像代码中的定海神针,一旦确立,雷打不动!它让你的代码更加健壮,可维护性蹭蹭上涨,还能有效防止手贱的同事(或者未来的你)不小心改了关键数值,引发线上事故!想想就刺激!😎

一、const:不仅仅是“恒定不变”那么简单!

const,英文直译就是“常量”,顾名思义,它定义的是一个一旦声明,就不能再改变的值。 想想看,如果圆周率 π 还能随便改,那数学界还不乱成一锅粥?代码世界也是一样,有些关键数据,必须像钢铁长城一样坚不可摧!

1. 全局常量 vs. 类常量:两种截然不同的舞台

在 PHP 中,const 有两种主要的使用场景:

  • 全局常量:define() 函数定义的常量,可以在代码的任何地方访问。
  • 类常量:const 关键字在类内部定义的常量,只能通过类本身或类的实例来访问。

咱们先来聊聊类常量,毕竟这才是今天的主角!

2. 类常量:类内部的坚实堡垒

类常量就像是类内部的“族规”,一旦制定,必须遵守!它通常用于定义类级别的配置信息、状态标志、或者一些固定不变的值。

语法结构:

class MyClass {
    const MY_CONSTANT = "Hello, world!";
}

//访问类常量:
echo MyClass::MY_CONSTANT; // 输出: Hello, world!

重点强调:

  • 类常量必须在类定义内部声明。
  • 类常量的值必须是编译时常量表达式,不能是变量、函数调用或者任何需要在运行时才能确定的值。
  • 类常量使用 类名::常量名 的方式访问。

二、const 的魅力:优点多到让你尖叫!

使用 const 关键字定义类常量,带来的好处简直不要太多!

1. 代码可读性爆表!

试想一下,你在一个庞大的项目中,看到一个数字 3.1415926,你可能一脸懵逼:这啥玩意儿?干嘛用的?但如果这个数字被定义成一个类常量 const PI = 3.1415926;,瞬间,代码的含义就清晰明了!就像在茫茫人海中看到了你初恋的微笑!🥰

2. 代码维护性UP! UP! UP!

如果项目中多处使用了同一个值,比如一个网站的默认语言,如果直接写死在代码里,一旦需要修改,那简直就是一场灾难!需要全局搜索替换,稍有不慎就会遗漏,导致bug满天飞!但如果定义成类常量,只需要修改一处,整个项目就更新了!简直就是程序员的福音!🙏

3. 杜绝手贱党!

常量的值是不可变的,这意味着,即使你手贱,或者你的同事(未来的你)手贱,想修改常量的值,PHP 也会毫不留情地抛出一个错误!这就像给你的代码加上了一把安全锁,防止意外发生!

4. 性能优化小能手!

PHP 解释器在编译时就会将常量的值确定下来,这意味着在运行时,访问常量比访问变量更快!虽然性能提升可能微乎其微,但在高并发场景下,积少成多,也能带来显著的优化效果!

三、const 的应用场景:让你的代码更上一层楼!

类常量的应用场景非常广泛,只要是需要在类级别定义的一些固定不变的值,都可以使用 const 关键字。

1. 定义配置信息:

class DatabaseConfig {
    const HOST = 'localhost';
    const USERNAME = 'root';
    const PASSWORD = 'password';
    const DATABASE = 'mydatabase';
}

// 使用:
$host = DatabaseConfig::HOST;

2. 定义状态标志:

class OrderStatus {
    const PENDING = 0;
    const PROCESSING = 1;
    const SHIPPED = 2;
    const COMPLETED = 3;
    const CANCELED = 4;
}

// 使用:
$orderStatus = OrderStatus::SHIPPED;

3. 定义数学常量:

class MathConstants {
    const PI = 3.14159265359;
    const E = 2.71828182846;
}

// 使用:
$circumference = 2 * MathConstants::PI * $radius;

4. 定义文件上传相关常量:

class UploadConfig{
    const MAX_FILE_SIZE = 2097152; //2MB
    const ALLOWED_EXTENSIONS = ['jpg', 'jpeg', 'png', 'gif'];
    const UPLOAD_DIR = '/uploads/';
}

5.定义API状态码:

class APIStatus {
    const SUCCESS = 200;
    const ERROR_BAD_REQUEST = 400;
    const ERROR_UNAUTHORIZED = 401;
    const ERROR_FORBIDDEN = 403;
    const ERROR_NOT_FOUND = 404;
    const ERROR_SERVER_ERROR = 500;
}

四、conststatic:傻傻分不清楚?No Problem!

很多小伙伴可能会把 conststatic 搞混,它们虽然都是在类级别定义的成员,但用途却截然不同。

特性 const (类常量) static (静态属性)
用途 定义不可变的值 定义类级别的变量
可变性 不可变 可变
访问方式 类名::常量名 类名::$属性名
初始化 必须在定义时初始化 可以延迟初始化
应用场景 定义配置信息、状态标志等 定义类级别的计数器、缓存等

举个栗子:

class Counter {
    const INITIAL_VALUE = 0; // 类常量,初始值
    public static $count = 0;  // 静态属性,计数器

    public static function increment() {
        self::$count++;
    }
}

echo Counter::INITIAL_VALUE; // 输出: 0
Counter::increment();
echo Counter::$count; // 输出: 1

总结一下:

  • const 定义的是常量,值不可变,用于存储类级别的配置信息或者固定不变的值。
  • static 定义的是静态属性,值可变,用于存储类级别的变量,比如计数器、缓存等。

五、const 的注意事项:避坑指南!

虽然 const 很好用,但也有一些需要注意的地方,一不小心就会掉进坑里!

1. 常量的值必须是编译时常量表达式!

这是最重要的一点!常量的值必须在编译时就能确定,不能是变量、函数调用或者任何需要在运行时才能确定的值。

// 错误示例:
class MyClass {
    const TIME = time(); // 报错!
}

2. 常量不能被重新赋值!

一旦定义了常量,就不能再改变它的值!否则 PHP 会抛出一个错误!

class MyClass {
    const MY_CONSTANT = "Hello, world!";
}

MyClass::MY_CONSTANT = "Goodbye, world!"; // 报错!

3. 常量的命名规范:

为了提高代码的可读性,建议使用大写字母和下划线来命名常量。

class MyClass {
    const MY_CONSTANT = "Hello, world!"; // 推荐
    const myConstant = "Hello, world!"; // 不推荐
}

4. 继承与常量:

子类可以访问父类的常量,但不能修改父类的常量。如果子类需要使用不同的值,可以使用 parent::常量名 访问父类常量,或者定义一个同名的常量来覆盖父类的常量。

class ParentClass {
    const MESSAGE = "Hello from parent!";
}

class ChildClass extends ParentClass {
    const MESSAGE = "Hello from child!"; // 覆盖父类常量
}

echo ParentClass::MESSAGE; // 输出: Hello from parent!
echo ChildClass::MESSAGE; // 输出: Hello from child!
echo ParentClass::MESSAGE; // 输出: Hello from parent!  还是输出parent的,说明child只是覆盖了,并没有修改

六、高级用法:常量表达式的进阶之路

虽然 const 的值必须是编译时常量表达式,但 PHP 7.4 及以上版本引入了一些新的特性,让常量表达式变得更加强大!

1. Typed Class Constants (PHP 7.4+)

PHP 7.4 允许你为类常量指定类型。这意味着你可以更加明确地定义常量的类型,提高代码的可读性和健壮性。

class MyClass {
    const int MY_INTEGER = 123;
    const string MY_STRING = "Hello, world!";
    const array MY_ARRAY = [1, 2, 3];
}

echo MyClass::MY_INTEGER; // 输出: 123
echo MyClass::MY_STRING; // 输出: Hello, world!
print_r(MyClass::MY_ARRAY); // 输出: Array ( [0] => 1 [1] => 2 [2] => 3 )

2. Constant Visibility (PHP 7.1+)

PHP 7.1 允许你为类常量设置访问修饰符(publicprotectedprivate),就像类属性一样。这意味着你可以更加精细地控制常量的访问权限。

class MyClass {
    public const PUBLIC_CONSTANT = "Public constant";
    protected const PROTECTED_CONSTANT = "Protected constant";
    private const PRIVATE_CONSTANT = "Private constant";

    public function accessConstants() {
        echo self::PUBLIC_CONSTANT . PHP_EOL;
        echo self::PROTECTED_CONSTANT . PHP_EOL;
        echo self::PRIVATE_CONSTANT . PHP_EOL;
    }
}

$obj = new MyClass();
$obj->accessConstants();

echo MyClass::PUBLIC_CONSTANT; // 可访问

// echo MyClass::PROTECTED_CONSTANT; // 报错,受保护的
// echo MyClass::PRIVATE_CONSTANT; // 报错,私有的

七、总结:const,你值得拥有!

今天我们深入探讨了 PHP 中 const 关键字的用法,从基本概念到高级特性,从应用场景到注意事项,相信各位观众老爷们已经对 const 有了更深刻的理解。

const 就像代码中的定海神针,它让你的代码更加健壮,可维护性蹭蹭上涨,还能有效防止手贱的同事(或者未来的你)不小心改了关键数值,引发线上事故!

所以,下次你在定义类级别的配置信息、状态标志或者一些固定不变的值时,不妨考虑使用 const 关键字,让你的代码更上一层楼!

好了,今天的分享就到这里,希望对大家有所帮助!如果觉得有用,记得点赞、收藏、转发哦!咱们下期再见!👋

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注