Ala*_*blo 12 php properties isset magic-methods
有很多关于这个问题的SO问题,特别是这个问题,但它对我没有帮助.
有之间的模糊性property_exists和isset如此前问我的问题,我要指出来:
property_exists检查对象是否包含属性而不查看其值,它只查看其可见性.
所以在下面的例子中:
<?php
class testA
{
private $a = null;
}
class testB extends testA
{
}
$test = new testA();
echo var_dump(property_exists($test, 'a')); // true
// parent's private property becomes invisible for its child
$test = new testB();
echo var_dump(property_exists($test, 'a')); // false
Run Code Online (Sandbox Code Playgroud)
isset检查属性中是否存在值 如果值等于false,和,则设置为未设置null.
<?php
$var = null;
echo var_dump(isset($var)); // false
$var = '';
echo var_dump(isset($var)); // true
$var = false;
echo var_dump(isset($var)); // true
$var = 0;
echo var_dump(isset($var)); // true
$var = '0';
echo var_dump(isset($var)); // true
Run Code Online (Sandbox Code Playgroud)
isset和property_exists魔法添加属性的行为属性可以存在null值,因此我不能使用__isset魔术方法来了解属性是否存在.我也无法使用property_exists魔术方法添加属性.
这是一个示例,但这只是一个示例,因为在我的应用程序中,魔法设置的属性存储在对象外部.
class test {
private $data = array();
public function __get($key) {
echo "get $key\n";
return array_key_exists($key, $data) ? $data[$key] : null;
}
public function __set($key, $value) {
echo "set $key = $value\n";
$this->data[$key] = $value;
}
public function __isset($key) {
echo sprintf("isset $key ( returns %b )", isset($this->data[$key]));
return isset($this->data[$key]);
}
}
$test = new test();
$test->x = 42;
isset($test->x); // 1
$test->y = null;
isset($test->y); // 0
property_exists($test, 'y'); // 0
Run Code Online (Sandbox Code Playgroud)
所以这是我的问题:
是否有神奇的方法或SPL接口来实现
property_exist神奇添加的属性?
我不相信有一种方法可以使用魔术方法改变property_exists()的功能; 这是PHP 中可用的魔术方法列表.但是,您应该能够更改isset()以使用您喜欢的任何逻辑.
class test {
private $data = array();
public function __get($key) {
echo "get $key\n";
return array_key_exists($key, $this->data) ? $this->data[$key] : null;
}
public function __set($key, $value) {
echo "set $key = $value\n";
$this->data[$key] = $value;
}
public function __isset($key) {
echo sprintf("isset $key ( returns %b )", array_key_exists($key, $this->data));
return array_key_exists($key, $this->data);
}
}
$test = new test();
$test->x = 42;
isset($test->x); // 1
$test->y = null;
isset($test->y); // 1
Run Code Online (Sandbox Code Playgroud)
这通过magic方法覆盖其功能,有效地修复了isset和null的(恼人的)问题.但是,我们不使用__isset()中的isset(),而是使用array_key_exists(它可以像您期望的那样处理空值).因此,__ isset()在设置空值时返回预期结果.
这有一个缺点,即被覆盖的功能不会产生与默认的isset()功能相同的结果.因此,如果此对象需要与其他(可能是stdClass)对象透明地使用,则isset()将对此类的对象中的空值返回true,对于普通对象中的空值则返回false.
根据您的需要,这可能是也可能不是一个可行的解决方案.如果上述问题是障碍,那么另一个选项可能是定义具有keyIsSet()属性的接口,并将该接口应用于所有要测试的对象.然后使用$ obj-> keyIsSet('key')而不是isset($ obj - > $ key).不是那么优雅,但更好一点oo.
| 归档时间: |
|
| 查看次数: |
9395 次 |
| 最近记录: |