Pregunta

Me gustaría poder escribir una clase PHP que se comporte como una matriz y use la sintaxis de matriz normal para obtener y configurar.

Por ejemplo (donde Foo es una clase PHP creada por mí):

$foo = new Foo();

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

echo $foo['fooKey'];

Sé que PHP tiene los métodos mágicos _get y _set, pero no te permiten usar la notación de matriz para acceder a los elementos.Python lo maneja sobrecargando __getitem__ y __setitem__.

¿Hay alguna manera de hacer esto en PHP?Si hay alguna diferencia, estoy ejecutando PHP 5.2.

¿Fue útil?

Solución

si extiendes ArrayObject o implementar ArrayAccess entonces puedes hacer lo que quieras.

Otros consejos

No, la conversión solo da como resultado una matriz PHP normal, perdiendo cualquier funcionalidad que tuviera su clase derivada de ArrayObject.Mira esto:

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";

Como era de esperar, la llamada a array_keys() falla.Además, is_array($blah) devuelve falso.Pero si cambias la línea del constructor a:

$blah = (array)new CaseInsensitiveArray(array(

entonces simplemente obtienes una matriz PHP normal (is_array($blah) devuelve verdadero y array_keys($blah) funciona), pero toda la funcionalidad de la subclase derivada de ArrayObject se pierde (en este caso, las claves que no distinguen entre mayúsculas y minúsculas ya no trabajar).Intente ejecutar el código anterior en ambos sentidos y verá lo que quiero decir.

PHP debería proporcionar una matriz nativa en la que las claves no distingan entre mayúsculas y minúsculas, o hacer que ArrayObject se pueda convertir en una matriz sin perder cualquier funcionalidad que implemente la subclase, o simplemente hacer que todas las funciones de la matriz acepten instancias de ArrayObject.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top