PHP中new static()与new self()的区别及替代方案
在PHP面向对象编程中,new self()与new static()常被用于类内部实例化当前对象,但两者表现截然不同。new self()始终指向定义该方法的具体类,而new static()利用后期静态绑定(Late Static Bindings)指向实际调用的子类。若需在不支持new static()的低版本环境(如PHP 5.2)中实现相同效果,可使用get_class($this)动态获取类名。
核心差异与执行结果
new self()的行为是固定的,它指的是代码段中出现的那一个类(即方法所在的类)。无论谁调用该方法,只要是在该类的方法体内使用self,创建的就是该类的实例。
new static()是PHP 5.3引入的“后期静态绑定”特性。它指向的是运行时被调用的那个类(当前实例化或发起调用的类)。这类似于$this的概念,但在静态上下文中,static解析的是调用层级中的最终类。
第1步:理解静态绑定的执行逻辑
我们可以通过继承关系直观地观察两者的行为差异。
class A {
public static function get_self() {
return new self();
}
public static function get_static() {
return new static();
}
}
class B extends A {}
echo get_class(B::get_self()); // 输出 A
echo get_class(B::get_static()); // 输出 B
echo get_class(A::get_static()); // 输出 A
上述示例中:
- B::get_self()虽然由B类调用,但get_self方法定义在A类中,因此new self()指向A类,结果为A。
- B::get_static()中new static()识别出调用者是B,故返回B类实例。
- A::get_static()中调用者为A,故返回A类实例。
第2步:解决低版本PHP兼容性问题的操作
如果在维护较老的项目(如要求兼容PHP 5.2),直接使用new static($val)会导致语法错误或功能缺失。此时可以通过动态类名实例化的方式实现相同的功能。
具体实现思路是利用get_class($this)获取当前对象的真实类名,并将其作为类名进行实例化。
class A {
// 兼容写法:通过反射当前实例获取类名
public function create1() {
$class = get_class($this);
return new $class();
}
// PHP 5.3+ 写法
public function create2() {
return new static();
}
}
class B extends A {
}
$b = new B();
var_dump(get_class($b->create1()), get_class($b->create2()));
/*
The result
string(1) "B"
string(1) "B"
*/
通过这种方式使用get_class($this),无论是在父类还是子类中调用,只要$this代表子类实例,生成的就是子类对象,从而完美替代new static()。
简要总结
new self()适合创建固定类型的单例或特定工厂模式;而new static()更适合需要在继承体系中保持多态性的场景。对于需要兼顾旧版PHP环境的开发任务,采用new (get_class($this))是稳健的替代方案。以上就是PHP中new static()与new self()的详细异同分析及应用技巧,更多关于PHP高级特性的资料请关注本站其它相关文章!
免责声明:本文内容仅供参考,不代表本站观点。转载或引用请注明出处。









