【发布时间】:2011-06-22 23:52:53
【问题描述】:
您可能知道,静态属性使测试变得困难。有没有办法将特定类的所有静态属性重置回初始状态?理想情况下,这不需要为每个类自定义代码,但可以通过继承以一般方式使用,或者完全从类外部使用。
请不要回复诸如“不要使用静态属性”之类的内容。谢谢。
【问题讨论】:
-
你在使用PHPUnit之类的测试框架吗?这将在测试模块的设置/拆卸例程中得到处理。
您可能知道,静态属性使测试变得困难。有没有办法将特定类的所有静态属性重置回初始状态?理想情况下,这不需要为每个类自定义代码,但可以通过继承以一般方式使用,或者完全从类外部使用。
请不要回复诸如“不要使用静态属性”之类的内容。谢谢。
【问题讨论】:
假设您使用的是 PHPUnit:
请参阅 PHPUnit 手册section about global state。如果您有 PHP 5.3 或更高版本,则静态成员会被涵盖在内。静态成员不是序列化的一部分(以防万一)。
【讨论】:
没有。 PHP 不保留该信息。
我在玩弄 ReflectionClass 和 ::getDefaultProperties 和 ::getStaticProperties,但它们只返回当前状态。
您必须使用默认值创建一个数组,然后手动遍历它们并重置您的类属性。
【讨论】:
getDefaultProperties 以获得默认值。
我找不到任何方法来多次包含或要求类或函数而不会出错。
无论如何,如果您需要替换结构中的函数,您应该创建一个 lamdas/内联函数 的 array/ArrayObject(如 javascript 对象)
当您重新导入数组时,它会恢复到原始状态。
$Animal = array(
'eat' => function($food) {/*...*/},
'run' => function($to_place) {/*...*/}
);
$Animal['eat'] = function($food) {/* new way to eat */}
我还设法通过使用反射来重置静态属性的状态。对于这种方法,您需要为每种类型的默认值使用约定属性命名。
class MyStaticHolder {
public static $x_array = array();
public static $x_num = 0;
public static $x_str = '';
}
//change values
MyStaticHolder::$x_array = array(1,2,4);
MyStaticHolder::$x_num = -1.4;
MyStaticHolder::$x_str = 'sample-text';
function reset_static($class_name) {
$z = new ReflectionClass($class_name);
$properties = $z->getDefaultProperties();
print_r($properties);
foreach ($properties as $property_name => $value) {
$sufix = end(explode('_',$property_name));
switch ($sufix) {
case 'array':
$class_name::$$property_name = array();
break;
case 'num':
$class_name::$$property_name = 0;
break;
case 'str':
$class_name::$$property_name = '';
break;
default:
$class_name::$$property_name = null;
break;
}
}
}
reset_static('MyStaticHolder');
【讨论】: