php重写父类方法无需特殊关键字,直接在子类定义同名同签名方法即可;private方法不可重写;final方法或类禁止重写;参数类型需兼容,推荐保持一致;用parent::调用父类方法。

PHP里重写父类方法不需要特殊关键字
PHP中重写(override)父类方法就是直接在子类里定义同名、同参数列表的方法,不需要 override、@Override 这类修饰符——这和Java、C#不同,PHP靠的是运行时方法查找机制。
只要子类有同签名的public或protected方法,调用时就会自动走子类版本;但注意:private方法不会被继承,更谈不上重写。
常见错误现象:Fatal error: Cannot override final method —— 父类方法加了 final 关键字,此时无法重写,必须删掉 final 或改用组合代替继承。
重写时参数数量和类型要小心匹配
PHP 7.2+ 开始严格检查重写方法的参数类型声明是否兼容。如果父类方法参数是 string,子类重写时不能改成 int,否则会报 Declaration of Child::method() must be compatible with Parent::method()。
实操建议:
- 子类方法参数类型必须是父类对应参数类型的「协变」(如父类接受
Animal,子类可接受Dog),但PHP目前仅支持返回值协变,参数仍是逆变约束,所以通常保持一致最安全 - 允许子类方法增加默认参数(如父类是
function foo($a),子类可写function foo($a, $b = null)),但调用方传两个参数时,父类接口其实没承诺支持,属于隐式扩展,需谨慎 - 使用
declare(strict_types=1)时,类型检查更严格,务必确保父子类类型声明完全兼容
怎么在子类方法里调用被重写的父类方法
用 parent::methodName() 显式调用父类实现,这是最常见的扩展模式(比如初始化前/后加逻辑)。
示例:
class Logger {
public function log($msg) {
echo "[LOG] $msg\n";
}
}
class JsonLogger extends Logger {
public function log($msg) {
parent::log($msg); // 先走父类基础输出
echo json_encode(['event' => $msg]) . "\n"; // 再追加JSON格式
}
}
注意点:
-
parent::只能访问public和protected方法,不能调private - 如果父类方法是
static,子类重写也得是static,调用时用parent::method()即可,不用self:: - 构造方法
__construct经常被重写,但忘了调parent::__construct()导致父类初始化逻辑丢失,这是高频疏漏点
final、static、abstract 组合下重写的限制
这些关键字会实质性改变重写行为,容易踩坑:
-
final方法不能被重写,否则直接致命错误;final类不能被继承,自然也无法重写任何方法 -
static方法可以被“重写”,但本质是类作用域屏蔽(late static binding),不是真正面向对象的多态;用self::调用的是定义该方法的类,而static::才是当前调用类(即支持静态延迟绑定) -
abstract方法必须被子类实现(即强制重写),且子类实现不能是abstract,否则报错
继承链越深,final 和 abstract 的约束叠加越容易让人忽略某一层的限制,建议在IDE里打开继承跳转,逐层确认可见性和修饰符。
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











