使PHP对象的行为类似于数组?

时间:2008-09-15 17:50:05

标签: php arrays oop

我希望能够编写一个行为类似于数组的PHP类,并使用常规数组语法来获取&设置。

例如(其中Foo是我制作的PHP类):

$foo = new Foo();

$foo['fooKey'] = 'foo value';

echo $foo['fooKey'];

我知道PHP有_get和_set魔术方法,但是那些不允许你使用数组表示法来访问项目。 Python通过重载__getitem__和__setitem __。

来处理它

有没有办法在PHP中执行此操作?如果它有所作为,我正在运行PHP 5.2。

2 个答案:

答案 0 :(得分:35)

如果您延长ArrayObject或实施ArrayAccess,那么您可以按照自己的意愿行事。

答案 1 :(得分:3)

Nope,只是导致一个普通的PHP数组 - 丢失了ArrayObject派生类所具有的任何功能。看看这个:

class CaseInsensitiveArray extends ArrayObject {
    public function __construct($input = array(), $flags = 0, $iterator_class =     'ArrayIterator') {
        if (isset($input) && is_array($input)) {
            $tmpargs = func_get_args();
            $tmpargs[0] = array_change_key_case($tmpargs[0], CASE_LOWER);
            return call_user_func_array(array('parent', __FUNCTION__), $tmp    args);
        }
        return call_user_func_array(array('parent', __FUNCTION__), func_get_args());
    }

    public function offsetExists($index) {
        if (is_string($index)) return parent::offsetExists(strtolower($index));
        return parent::offsetExists($index);
    }

    public function offsetGet($index) {
        if (is_string($index)) return parent::offsetGet(strtolower($index));
        return parent::offsetGet($index);
    }

    public function offsetSet($index, $value) {
        if (is_string($index)) return parent::offsetSet(strtolower($index, $value));
        return parent::offsetSet($index, $value);
    }

    public function offsetUnset($index) {
        if (is_string($index)) return parent::offsetUnset(strtolower($index));
        return parent::offsetUnset($index);
    }
}

$blah = new CaseInsensitiveArray(array(
    'A'=>'hello',
    'bcD'=>'goodbye',
    'efg'=>'Aloha',
));

echo "is array: ".is_array($blah)."\n";

print_r($blah);
print_r(array_keys($blah));

echo $blah['a']."\n";
echo $blah['BCD']."\n";
echo $blah['eFg']."\n";
echo $blah['A']."\n";

正如预期的那样,array_keys()调用失败。另外,is_array($ blah)返回false。但是,如果将构造函数行更改为:

$blah = (array)new CaseInsensitiveArray(array(

然后你得到一个普通的PHP数组(is_array($ blah)返回true,并且array_keys($ blah)工作),但是ArrayObject派生的子类的所有功能都丢失了(在这种情况下,不区分大小写)钥匙不再起作用)。尝试两种方式运行上面的代码,你会明白我的意思。

PHP应该提供一个本地数组,其中键不区分大小写,或者使ArrayObject可以转换为数组而不会丢失子类实现的任何功能,或者只是让所有数组函数都接受ArrayObject实例。