问题
我是开源的一个特点,其中包括神奇的方法__call()。在测试期间,当使用该特性的类的父类包含__call方法时,我遇到了一个挑战。
我试过的
trait SomeTrait {
public function __call($method, array $parameters) {
// ...
return parent::__call($method, $parameters);
}
}这将导致致命错误:当当前类范围没有父类时,无法访问父类::
我还在其他一些answers的基础上尝试了以下内容
return call_user_func_array([$this, '__call'], [$method, $parameters]);这导致了分割错误: 11。我想是因为一个无限的调用循环。
问题
如何从特征的__call方法中调用父级的__call方法?
如果不能直接从特征内部调用,我如何调用父级的__call方法呢?
发布于 2015-05-26 15:06:59
请检查下面的代码:
trait SomeTrait
{
public function __call($method, array $parameters)
{
// ...
return is_callable(['parent', '__call']) ? parent::__call($method, $parameters) : null;
}
}
class GreatParentClass
{
public function __call($method, array $parameters)
{
return 'bar';
}
}
class ParenClassWithoutCall
{
}
class ProxyClass extends GreatParentClass
{
}
class FooClass extends ProxyClass
{
use SomeTrait;
}
class BarClass extends GreatParentClass
{
use SomeTrait;
}
class BazClass extends ParenClassWithoutCall
{
use SomeTrait;
}
class SomeClassWithoutParent
{
use SomeTrait;
}
$class = new FooClass();
var_dump($class->foobar());
$class = new BarClass();
var_dump($class->foobar());
$class = new BazClass();
var_dump($class->foobar());
$class = new SomeClassWithoutParent();
var_dump($class->foobar());这将打印:
string(3) "bar"
string(3) "bar"
NULL
NULL带有要检查的代码的沙箱:http://3v4l.org/R8hI3
编辑:我认为这将涵盖所有的可能性。
发布于 2015-05-26 15:18:48
这里的问题是,如果在没有父类的类中使用此特性,则此调用将失败。在调用父函数之前,可以考虑检查类是否有父函数。看起来可能是这样:
trait SomeTrait {
public function __call($method, array $parameters) {
// ...
if (count(class_parents($this)) {
return parent::__call($method, $parameters);
}
}
}我也要说,这可能不是最好的设计方法。我不认为应该呈现可移植的、可组合的功能集的特性应该在采用类的继承链中改变/覆盖功能。
https://stackoverflow.com/questions/30460329
复制相似问题