Ricardo
Ricardo

Reputation: 23

Recursive array from structure with only childids

I have a structure like this

$list = array(
  array('code'=>1,'children'=>array(2,3),'name'=>'number one'),
  array('code'=>2,'children'=>array(4),'name'=>'number two'),
  array('code'=>3,'children'=>array(5,6),'name'=>'number three'),
  array('code'=>4,'children'=>array(7),'name'=>'number four'),
  array('code'=>5,'children'=>array(),'name'=>'number five'),
  array('code'=>6,'children'=>array(8),'name'=>'number six'),
  array('code'=>7,'children'=>array(),'name'=>'number seven'),
  array('code'=>8,'children'=>array(),'name'=>'number eight')
);

and I need the return to be

array(
  array('code'=>1,'children'=>array(
    array('code'=>2,'children'=>array(
      array('code'=>4,'children'=>array(7),'name'=>'number four'),
    ),'name'=>'number two'),
    array('code'=>3,'children'=>array(
       array('code'=>5,'children'=>array(),'name'=>'number five'),
       array('code'=>6,'children'=>array(
          array('code'=>8,'children'=>array(),'name'=>'number eight')
       ),'name'=>'number six'),
    ),'name'=>'number three'),
  ),'name'=>'number one')
);

Note that I don't have a parent id, only children id. and the id isn't a key (although I can make a foreach and make a key from it). Any ideas on how I can make this with minimal passages?

Upvotes: 1

Views: 59

Answers (1)

chiliNUT
chiliNUT

Reputation: 19592

How about this:

//2 pass:

//#1 add keys, objectify
$output = array();
foreach ($list as $k => $el) {
    $output[$k + 1] = (object) $el;
}

//#2 build
foreach($output as $k=>$el) {
    if (!empty($el->children)) {
        $children=$el->children;
        $output[$k]->children=array();
        foreach($children as $childID) {
            $output[$k]->children[]=$output[$childID];
        }
    } else {
        //remove it, no child nodes
        unset($output[$k]->children);
    }
}

so, $output[1] has our tree, and the rest of $output can be discarded since it is essentially just extra references to the nodes attached to 1.

$tree=$output[1];

print_r($tree);
stdClass Object
(
    [code] => 1
    [children] => Array
        (
            [0] => stdClass Object
                (
                    [code] => 2
                    [children] => Array
                        (
                            [0] => stdClass Object
                                (
                                    [code] => 4
                                    [children] => Array
                                        (
                                            [0] => stdClass Object
                                                (
                                                    [code] => 7
                                                    [name] => number seven
                                                )

                                        )

                                    [name] => number four
                                )

                        )

                    [name] => number two
                )

            [1] => stdClass Object
                (
                    [code] => 3
                    [children] => Array
                        (
                            [0] => stdClass Object
                                (
                                    [code] => 5
                                    [name] => number five
                                )

                            [1] => stdClass Object
                                (
                                    [code] => 6
                                    [children] => Array
                                        (
                                            [0] => stdClass Object
                                                (
                                                    [code] => 8
                                                    [name] => number eight
                                                )

                                        )

                                    [name] => number six
                                )

                        )

                    [name] => number three
                )

        )

    [name] => number one
)

my structure differs slightly than yours since I used objects, which are better suited to this in that they are accessed by reference, which is what you want when dealing with nodes. And if this is JSON it will likely become an object anyway.

Upvotes: 1

Related Questions