Take the 2-minute tour ×
Stack Overflow is a question and answer site for professional and enthusiast programmers. It's 100% free, no registration required.

I'm trying to sort a multidimensional array down to a sorted, one-dimensional array where values on the same level are merged together ordered by key alternating between it's parents.

So start with this array:

Array
(
    [0] => Array
        (
            [0] => Array
                (
                    [0] => 60
                    [1] => 68
                    [2] => 71
                    [3] => 72
                )

        )

    [1] => Array
        (
            [0] => Array
                (
                    [0] => 61
                    [1] => 62
                    [2] => 64
                )

            [1] => Array
                (
                    [0] => 69
                    [1] => 70
                )

        )

    [2] => Array
        (
            [0] => Array
                (
                    [0] => 63
                )

            [1] => Array
                (
                    [0] => 65
                    [1] => 66
                )

        )

    [3] => Array
        (
            [0] => Array
                (
                    [0] => 66
                )

        )

)

and end up with this:

Array
(
    [0] => 60
    [1] => 68
    [2] => 71
    [3] => 72
    [4] => 61
    [5] => 69
    [6] => 62
    [7] => 70
    [8] => 64
    [9] => 63
    [10] => 65
    [11] => 66
    [12] => 67
)

I tried something from this question like this:

function merge_common_keys(){
    $arr = func_get_args();
    $num = func_num_args();

    $keys = array();
    $i = 0;
    for($i=0;$i<$num;++$i){
        $keys = array_merge($keys, array_keys($arr[$i]));
    }

    $keys = array_unique($keys);

    $merged = array();

    foreach($keys as $key){
        for($i=0;$i<$num;++$i){
            if(isset($arr[$i][$key])){
                $merged[] = $arr[$i][$key];
            }
        }
    }

    return $merged;
}

but it requires passing in multiple arrays and I can't figure out how to feed it just one big array and recursive walk down it.

share|improve this question
add comment

2 Answers

up vote 0 down vote accepted

This is what I came up with:

function array_builder($array) {
    $output = array();
    foreach($array as $level1) {
        if(count($level1) > 1) {
            $counts = array();
            foreach($level1 as $level2) {
                $counts[] = count($level2);
            }
            $largest = max($counts);
            $level2_count = count($level1);
            for($x=0;$x<$largest;$x++) {
                for($y=0;$y<$level2_count;$y++) {
                    if(isset($level1[$y][$x])) {
                        $output[] = $level1[$y][$x];
                    }
                }
            }
        } else {
            $output = array_merge($output,$level1[0]);
        }
    }
    return $output;
}

A print_r() will give you this:

Array ( 
    [0] => 60 
    [1] => 68 
    [2] => 71
    [3] => 72
    [4] => 61
    [5] => 69
    [6] => 62
    [7] => 70
    [8] => 64
    [9] => 63
    [10] => 65
    [11] => 66
    [12] => 66 
)
share|improve this answer
 
This works perfectly - thank you. –  davelassanske Jan 21 at 22:06
add comment

An attempt with php 5.4: (may have been shorter on php 5.5 with array_column).

function flattenAndVentilate(array $array)
{
    $result = array();
    foreach ($array as $array_l1) {
        $copy = $array_l1;
        // get level2 count()s in $copy array
        array_walk($copy, function(&$value,$key){$value=count($value);});
        $maxsize = max($copy);
        for ($i=0;$i<$maxsize;$i++) {
            foreach ($array_l1 as $array_l2) {
                if (isset($array_l2[$i])) {
                    $result[] = $array_l2[$i];
                }
            }
        }
    }

    return $result;
}

print_r(flattenAndVentilate($array));

outputs :

Array
(
    [0] => 60
    [1] => 68
    [2] => 71
    [3] => 72
    [4] => 61
    [5] => 69
    [6] => 62
    [7] => 70
    [8] => 64
    [9] => 63
    [10] => 65
    [11] => 66
    [12] => 66
)
share|improve this answer
 
That isn't what they want. They want it sorted a very specific way. –  Pitchinnate Jan 21 at 21:01
 
It is now (updated). –  Calimero Jan 21 at 21:24
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.