0

I need to flatten a PHP array but having some issues getting the desired results.

Array
(
[0] => Array
    (
        [case_code_id] => 1
        [parent_id] => 0
        [case_code] => Main A
        [sub_codes] => Array
            (
                [0] => Array
                    (
                        [case_code_id] => 3
                        [parent_id] => 1
                        [case_code] => Sub A
                        [sub_codes] => Array
                            (
                                [0] => Array
                                    (
                                        [case_code_id] => 5
                                        [parent_id] => 3
                                        [case_code] => Sub Sub A
                                        [sub_codes] => Array
                                            (
                                            )

                                    )

                            )

                    )

                [1] => Array
                    (
                        [case_code_id] => 4
                        [parent_id] => 1
                        [case_code] => Sub B
                        [sub_codes] => Array
                            (
                            )

                    )

            )

    )

[1] => Array
    (
        [case_code_id] => 2
        [parent_id] => 0
        [case_code] => Main B
        [sub_codes] => Array
            (
            )

    )

)

But I would like to convert this to the following:

Array
(
    [0] => Array
    (
        [case_code_id] => 1
        [parent_id] => 0
        [case_code] => Main A
    )
    [1] => Array 
    (
        [case_code_id] => 3
        [parent_id] => 1
        [case_code] => Sub A
    )
    [2] => Array
    (
        [case_code_id] => 5
        [parent_id] => 3
        [case_code] => Sub Sub A
    )
    [3] => Array
    (
        [case_code_id] => 4
        [parent_id] => 1
        [case_code] => Sub B
    )
    [4] => Array
    (
        [case_code_id] => 2
        [parent_id] => 0
        [case_code] => Main B
        [sub_codes] => Array
    )

I have tried several loops but nothing returns the full array.

Here is what I have for my loop:

public function array_flatten($array,$list=array()){
    for ($i=0;$i<count($array);$i++) {
        $results[] = array(
            'case_code_id'=>$array[$i]['case_code_id'],
            'case_code'=>$array[$i]['case_code'],
            'parent_id'=>$array[$i]['parent_id']
        );
        if (count($array[$i]['sub_codes']) > 0) {
            $this->array_flatten($array[$i]['sub_codes'],$results);
        } else {
            $results[] = $array[$i];
        }
    }
    return $results;
}

And I'm calling it like this: ($multi contains the multidimensional array)

  $flat = $this->array_flatten($multi); 

The variable $multi is created from this function:

public function build_case_code_tree(array $elements, $parentId = 0) {
    $branch = array();
    foreach ($elements as $element) {
        if ($element['parent_id'] == $parentId) {
            $children = $this->build_case_code_tree($elements, $element['case_code_id']);
            $element['sub_codes'] = $children;
            $branch[] = $element;
        }
    }
    return $branch;
}

Any thoughts?

Dan Glauber
  • 19
  • 1
  • 3
  • Possible duplicate of [How to "flatten" a multi-dimensional array to simple one in PHP?](https://stackoverflow.com/questions/526556/how-to-flatten-a-multi-dimensional-array-to-simple-one-in-php) – Eliya Cohen Sep 25 '18 at 19:45
  • 1
    The suggested post did not produce the results I'm looking for. This is what the output looked like Array ( [0] => 1 [1] => 0 [2] => Main A [3] => 3 [4] => 1 [5] => Sub A [6] => 5 [7] => 3 [8] => Sub Sub A [9] => 4 [10] => 1 [11] => Sub B [12] => 2 [13] => 0 [14] => Main B ) – Dan Glauber Sep 25 '18 at 19:47
  • It would be super helpful if you could provide the initiation of `$multi` for us instead of expecting us to mock up our own data based on your `print_r()`. It generally helps you to get relevant and working answers when you provide an easy way for us to test the sample data... – MonkeyZeus Sep 25 '18 at 20:11
  • I added the function the generates the multi array. – Dan Glauber Sep 25 '18 at 20:33

2 Answers2

1
function array_flatten($a, $flat = []) {
    $entry = [];
    foreach ($a as $key => $el) {
        if (is_array($el)) {
            $flat = array_flatten($el, $flat);
        } else {
            $entry[$key] = $el;
        }
    }
    if (!empty($entry)) {
        $flat[] = $entry;
    }
    return $flat;
}
print_r(array_flatten($multi));
steffen
  • 16,138
  • 4
  • 42
  • 81
0

You're not using $list anywhere in the code, and nothing is passed by reference. You're close, but your function should use $list in the place of $results, and it should receive $list by reference and modifying it in place instead of returning it.

Something like this (untested though):

function array_flatten($array,&$list=array()){
    for ($i=0;$i<count($array);$i++) {
        $list[] = array(
            'case_code_id'=>$array[$i]['case_code_id'],
            'case_code'=>$array[$i]['case_code'],
            'parent_id'=>$array[$i]['parent_id']
        );
        if (count($array[$i]['sub_codes']) > 0) {
            $this->array_flatten($array[$i]['sub_codes'],$list);
        } else {
            $list[] = $array[$i];
        }
    }
}

And calling it like this:

$flat = Array();
$this->array_flatten($multi, $flat);
// Result is inside $flat now
henry700
  • 179
  • 3
  • 8