PHP echo语句中的无限递归

Dra*_*kes 3 php recursion tostring infinite-loop

为什么这段代码会导致无限递归?

class Foo {
    public static function newFoo() { return new Foo(); }
    public function __toString() {
        return "{${Foo::newFoo()}}";
    }
}

echo new Foo(); // Infinite recursion
new Foo();      // Finishes normally
Run Code Online (Sandbox Code Playgroud)

这是因为__toString()返回一个对象吗?但这是不可能的,因为根据文档

此方法必须返回一个字符串,否则会发出致命的E_RECOVERABLE_ERROR级别错误.(参考)

或者它只是在__toString()方法中无限递归?

Mat*_*ari 7

echo new Foo();
Run Code Online (Sandbox Code Playgroud)

创建一个Foo并尝试echo它,为此,它将对象转换为字符串调用魔术方法__toString.

但是,在该方法中,您调用静态方法Foo::newFoo,该方法返回一个新对象,该对象再次被转换为字符串__toString本身,因此再次调用它.

所以,是的,这是无限递归.

澄清:

public function __toString() {
    return "{${Foo::newFoo()}}";
}
Run Code Online (Sandbox Code Playgroud)

相当于

public function __toString() {
    $foo = Foo::newFoo();
    return "$foo"; // this is a cast as string, which invokes __toString() again.
}
Run Code Online (Sandbox Code Playgroud)