PHP Recursively Convert Object to Array

13,682

Solution 1

You want to check if it's an object not an array, though you might do both:

if (is_object($attribute) || is_array($attribute)) $attribute = $this->object_to_array($attribute);
//I don't see a need for this
//if (!is_string($attribute)) $attribute = (array) $attribute;

And from Aziz Saleh, reference $attribute so you can modify it:

foreach ($array as &$attribute) {

Solution 2

Here's my version. First it will test if the parameter passed is an array or object. If so it'll convert to array (if necessary) then run through each element (by reference) and recursively run the function on it. When it gets to a scalar value it will just return the value unmodified. Seems to work :-)

function object_to_array($obj) {
    //only process if it's an object or array being passed to the function
    if(is_object($obj) || is_array($obj)) {
        $ret = (array) $obj;
        foreach($ret as &$item) {
            //recursively process EACH element regardless of type
            $item = object_to_array($item);
        }
        return $ret;
    }
    //otherwise (i.e. for scalar values) return without modification
    else {
        return $obj;
    }
}

Solution 3

You need to operate recursively.

This is the shortest I could come up with:

$toArray = function($x) use(&$toArray)
{
    return is_scalar($x)
        ? $x
        : array_map($toArray, (array) $x);
};

$array = $toArray($object);

Solution 4

Try using PHPs built in ArrayObject. It allows you to treat an object as an array.

http://www.php.net/manual/en/class.arrayobject.php

Share:
13,682
735Tesla
Author by

735Tesla

Computers make a fun hobby. If only keybase had support for stack exchange accounts :(

Updated on June 08, 2022

Comments

  • 735Tesla
    735Tesla almost 2 years

    I am trying to recursively convert a php object to an array. The function I wrote is this:

    public function object_to_array($obj) {
        $array = (array) $obj;
        foreach ($array as $attribute) {
          if (is_array($attribute)) $attribute = $this->object_to_array($attribute);
          if (!is_string($attribute)) $attribute = (array) $attribute;
        }
        return $array;
    }
    

    However, I still end up with objects in my outer array. Why is this? Is my function incorrect?

  • 735Tesla
    735Tesla about 10 years
    The second part checking if it's a string is because I'm ultimately turning it into json. If it's a string I don't need to split it further.
  • AbraCadaver
    AbraCadaver about 10 years
    If its not a string you are casting it to an array with (array). So ints, floats, booleans will be an array.
  • 735Tesla
    735Tesla about 10 years
    I thought that I was saying if it is not a string, then cast it to an array? Doesn't ! invert the condition?
  • AbraCadaver
    AbraCadaver about 10 years
    Yes, i edited it. It casts ints, floats, booleans to an array.
  • 735Tesla
    735Tesla about 10 years
    Thanks. This works great! A bit too well though, now it also dumps the user's password hashes and reset/persist codes. Obviously that shouldn't be in the api :P I have to check if it is something I don't want to be included in the loop and remove it.
  • MAChitgarha
    MAChitgarha almost 5 years
    It performs 1.5x to 2x faster than json_decode() + json_encode().
  • Elia Weiss
    Elia Weiss over 4 years
    I couldn't find any proper documentation to ArrayObject
  • 2pha
    2pha over 3 years
    this worked well except for null values so I replaced return is_scalar($x) with return (is_scalar($x) || is_null($x))