PHP怎样声明变量为只读属性

来源:IT编程作者:Ada头衔:草根站长
导读:本期聚焦于小伙伴创作的《PHP怎样声明变量为只读属性》,敬请观看详情,探索知识的价值。以下视频、文章将为您系统阐述其核心内容与价值。如果您觉得《PHP怎样声明变量为只读属性》有用,将其分享出去将是对创作者最好的鼓励。

在PHP开发中,声明只读变量可以有效避免变量被意外修改,提升代码的健壮性和可维护性。PHP提供了多种不同的方式来实现只读变量的效果,不同方式适用于不同的开发场景。

PHP怎样声明变量为只读属性

使用const声明类常量

const关键字可以在类中声明常量,类常量一旦定义就不能被修改,属于只读属性。类常量不需要实例化类就可以访问,访问时使用双冒号语法。

<?php
class User {
    // 声明类常量,属于只读属性
    const ROLE_ADMIN = 1;
    const ROLE_NORMAL = 2;
    
    public function getRoleName($role) {
        if ($role == self::ROLE_ADMIN) {
            return '管理员';
        } elseif ($role == self::ROLE_NORMAL) {
            return '普通用户';
        }
        return '未知角色';
    }
}

// 访问类常量,不需要实例化对象
echo User::ROLE_ADMIN; // 输出1

// 尝试修改类常量会报错
// User::ROLE_ADMIN = 3; // 这行代码会触发错误
?>

需要注意的是,const声明的常量只能在类、接口或者全局作用域中使用,不能在函数内部或者普通代码块中声明。而且类常量的值必须是固定的,不能是变量、表达式或者函数调用的结果。

使用define声明全局常量

define函数可以声明全局常量,全局常量在整个脚本执行过程中都是只读的,不能被重新赋值。全局常量可以在任何作用域中访问,不需要额外的访问语法。

<?php
// 声明全局常量
define('APP_NAME', '用户管理系统');
define('APP_VERSION', '1.0.0');

// 访问全局常量
echo APP_NAME; // 输出用户管理系统

// 尝试修改全局常量会报错
// define('APP_NAME', '新的系统名称'); // 重复定义常量会触发警告,值不会被修改
// APP_NAME = '测试'; // 直接赋值会触发错误
?>

define声明的常量默认是大小写敏感的,如果需要大小写不敏感的常量,可以在define函数的第三个参数传入true。另外,PHP7之后define也支持声明数组类型的常量。

使用readonly关键字(PHP8.1+)

PHP8.1版本新增了readonly关键字,可以用于声明类的只读属性。只读属性只能在声明时或者构造函数中赋值,之后就不能被修改,不管是类内部还是外部都不可以修改。

<?php
class Product {
    // 声明只读属性
    public readonly string $name;
    public readonly float $price;
    
    public function __construct(string $name, float $price) {
        // 构造函数中为只读属性赋值
        $this->name = $name;
        $this->price = $price;
    }
    
    public function getInfo() {
        return "商品名称:{$this->name},价格:{$this->price}";
    }
}

$product = new Product('笔记本电脑', 4999.99);
echo $product->getInfo(); // 输出商品名称:笔记本电脑,价格:4999.99

// 尝试修改只读属性会报错
// $product->name = '手机'; // 这行代码会触发错误
?>

readonly关键字只能用于类的属性,不能用于普通变量。而且只读属性必须指定类型,不能是mixed类型,也不能有默认值(除非默认值是null且属性类型为nullable)。

通过类的getter方法模拟只读属性

在PHP8.1之前,我们可以通过将属性设置为私有,只提供getter方法不提供setter方法的方式,模拟只读属性的效果。这种方式可以在getter方法中添加额外的逻辑,比如数据校验或者格式化。

<?php
class Order {
    private string $orderId;
    private string $createTime;
    
    public function __construct() {
        $this->orderId = uniqid('order_');
        $this->createTime = date('Y-m-d H:i:s');
    }
    
    // 只读属性的getter方法
    public function getOrderId(): string {
        return $this->orderId;
    }
    
    public function getCreateTime(): string {
        return $this->createTime;
    }
}

$order = new Order();
echo $order->getOrderId(); // 输出订单ID
echo $order->getCreateTime(); // 输出创建时间

// 无法直接修改私有属性,模拟只读效果
// $order->orderId = 'new_id'; // 这行代码会触发错误
?>

这种方式的缺点是访问属性时需要使用方法调用,不能直接通过对象->属性的方式访问,不过可以通过__get魔术方法优化访问体验,但需要注意__get魔术方法会影响所有未定义或未公开属性的访问。

不同只读变量方式的对比

下面是几种只读变量声明方式的对比,方便开发者根据需求选择:

方式适用场景是否支持动态赋值访问方式
const类常量类相关的固定不变的值否,值必须是固定值类名::常量名
define全局常量全局范围的固定配置值否,值必须是固定值直接写常量名
readonly属性PHP8.1+,类的实例相关的只读属性是,可在构造函数赋值对象->属性名
getter模拟PHP8.1之前,需要额外逻辑的只读属性是,可在构造函数赋值对象->getXxx()方法

在实际开发中,如果是全局的固定配置,优先选择define或者const全局常量;如果是类的固定属性,选择const类常量;如果是PHP8.1以上版本的类的实例属性只读需求,优先使用readonly关键字;如果是低版本PHP或者需要额外逻辑的只读属性,使用getter方法模拟。

PHP只读变量constreadonly属性声明修改时间:2026-07-21 19:36:30

免责声明:​ 已尽一切努力确保本网站所含信息的准确性。网站内容多为原创整理与精心编撰,观点力求客观中立。本站旨在免费分享,内容仅供个人学习、研究或参考使用。若引用了第三方作品,版权归原作者所有。如内容涉及您的权益,请联系我们处理。
内容垂直聚焦
专注技术核心技术栏目,确保每篇文章深度聚焦于实用技能。从代码技巧到架构设计,为用户提供无干扰的纯技术知识沉淀,精准满足专业提升需求。
知识结构清晰
覆盖从开发到部署的全链路。AI、前端、编程、数据库、服务器、建站、系统层层递进,构建清晰学习路径,帮助用户系统化掌握开发与运维所需的核心技术。
深度技术解析
拒绝泛泛而谈,深入技术细节与实践难点。无论是数据库优化还是服务器配置,均结合真实场景与代码示例进行剖析,致力于提供可直接应用于工作的解决方案。
专业领域覆盖
精准对应开发生命周期。从前端界面到后端编程,从数据库操作到服务器运维,形成完整闭环,一站式满足全栈工程师和运维人员的技术需求。
即学即用高效
内容强调实操性,步骤清晰、代码完整。用户可根据教程直接复现和应用于自身项目,显著缩短从学习到实践的距离,快速解决开发中的具体问题。
持续更新保障
专注既定技术方向进行长期、稳定的内容输出。确保各栏目技术文章持续更新迭代,紧跟主流技术发展趋势,为用户提供经久不衰的学习价值。