考虑以下代码:
class A {
function __construct() { echo __FUNCTION__ . "n"; }
function __destruct() { echo __FUNCTION__ . "n"; }
}
$a = new A();
$c = new ReflectionClass($a);
$c->isCloneable();
只是实例化一个新类,并使用反射检查它是否可克隆。
输出异常:
__construct
__destruct
__destruct
为什么__destruct
呼叫两次?在查看PHP源代码后,似乎在ext/php_reflection/reflection.c
ZEND函数isCloneable
发生调用zval_dtor(&obj)
时,反射对象没有定义__clone()
方法。因此,将__clone()
添加到类中可以修复双析构函数问题。那是什么?PHP中的Bug ?
注:
显然在7.3.5中仍然存在问题。
看起来调用isclable会运行析构函数。它不调用构造函数。如果你添加__clone,它什么都不调用。
我的解决方案是确保析构函数可以在未初始化的类上运行(而不是成员变量的默认设置)。
在这里提交bug报告:https://bugs.php.net/bug.php?id=79115。