我正在用 PHP 5.3 编写一个库,其中大部分是一个具有几个静态属性的类,这些静态属性由子类扩展以允许子类的零配置。
无论如何,这里有一个示例来说明我发现的特殊性:
<?php
class A {
protected static $a;
public static function out() { var_dump(static::$a); }
public static function setup($v) { static::$a =& $v; }
}
class B extends A {}
class C extends A {}
A::setup('A');
A::out(); // 'A'
B::out(); // null
C::out(); // null
B::setup('B');
A::out(); // 'A'
B::out(); // 'B'
C::out(); // null
C::setup('C');
A::out(); // 'A'
B::out(); // 'B'
C::out(); // 'C'
?>
现在,就我而言,这对于静态继承来说是非常理想的行为,但是,更改static::$a =& $v;
为static::$a = $v;
(无引用)你会得到我期望的行为,即:
'A'
'A'
'A'
'B'
'B'
'B'
'C'
'C'
'C'
谁能解释这是为什么?我无法理解引用如何以任何方式影响静态继承:/
更新:
根据Artefacto 的回答,在基类(在本例中为 A)中具有以下方法并在类声明之后调用它会产生上面标记为“所需”的行为,而无需在设置器中通过引用进行分配,同时保留结果当使用 self:: 作为上面的“预期”行为时。
/*...*/
public static function break_static_references() {
$self = new ReflectionClass(get_called_class());
foreach($self->getStaticProperties() as $var => $val)
static::$$var =& $val;
}
/*...*/
A::break_static_references();
B::break_static_references();
C::break_static_references();
/*...*/