从现有数组值创建多维子数组

时间:2013-11-19 08:44:56

标签: php arrays sorting nested

我一直在讨论这个问题,我希望有人能为此做出创造性的解决方案。 简而言之,我们从数据库中提取信息,并希望使用一些结果列创建嵌套数组,按其值排序和分组;

结果可能看起来像这样,它总是一个单级数组的数组:

Array (
    [0] => Array (
        ['day'] => 'a',
        ['stuff'] => 'b',
        ['nested3'] => 'c',
        ['data1'] => 'park',
        ['data2'] => 'sunny'
    ),
    [1] => Array (
        ['day'] => 'a',
        ['stuff'] => 'b',
        ['nested3'] => 'c',
        ['data1'] => 'store',
        ['data2'] => 'sunny'
    ),
    [2] => Array (
        ['day'] => 'a',
        ['stuff'] => 'z',
        ['nested3'] => 'c',
        ['data1'] => 'home',
        ['data2'] => 'rainy'
    ),
)

在这里,我想创建一个新的嵌套数组,按照“嵌套”命名类型列的数量深度分组X级别。请注意,'嵌套'命名方案仅作为示例,实际的列名称可以是任何东西,并且可以是3列深,以便排序,或者更多或更少 - 因此,排序循环的硬编码不是一种选择。

Array (
    'a' => Array (
        'b' => Array ( 
            'c' => Array (
                [0] => Array (
                    'data1' => 'park',
                    'data2' => 'sunny'
                ),
                [1] => Array (
                    'data1' => 'store',
                    'data2' => 'sunny'
                )
            )
        ),
        'z' => Array (
            'c' => Array (
                'data1' => 'home',
                'data2' => 'rainy'
            )
        )
    )
)

这将用于生成树样式的html表。不幸的是,似乎PDO的fetch不支持多列分组,所以我需要自己做饭。

您会注意到数据最初是关联的 - 因为我从PDO中提取它也可以用数字方式编制索引,这部分无关紧要,因为我会提前知道数据的顺序。

我会提前知道嵌套列的深度是多少列,所以这样的东西会起作用:

function nest_sort(&arr, $sort_col_count) {
    ...
}

或函数我可以按嵌套顺序指定用于排序的列的名称

function nest_sort(& arr,$ sort_columns)         //按$ sort_columns值排序$ arr         //以$ sort_columns的嵌套顺序     }     nest_sort($ array,array('nested1','nested2'))

它可以处理相当大的数据集,1000行数据。所以资源是值得关注的。

我已经做了很多尝试,我最大的挂断事实是排序深度不是难以预测的,编写递归函数从它自己创建嵌套数组就是PITA。

我不禁认为使用array_walk_recursive和/或array_merge递归有一种更简单,更高效的方法来实现这一点。

赞赏所有人。

1 个答案:

答案 0 :(得分:0)

那么, 经过更多的测试,我终于有了一个功能齐全的作品现在生病只需要完成表生成。 它将通过引用传递要排序的数组,以便在内存时释放内存。

$a[] = array('one', 'two', 'three', 'win', 'ner');
$a[] = array('one', 'two', 'three', 'win', 'dog');
$a[] = array('one', 'two', 'three', 'lost', 'cat');
$a[] = array('one', 'two', 'five', 'win', 'ner');
$a[] = array('one', 'two', 'five', 'lost', 'ner');

function dep(&$a, $depth) {

    $count = count($a);
    for($z = 0; $z < $count; $z++) {
        unset($tmp);
        $ptr = &$tmp;

        for($x = 0; $x <= $depth; $x++) {   
            $old = $new; 
            $new = array_shift($a[$z]);
            if($x == 0) continue;

            $ptr = &$ptr[$old];
            if($x == $depth) {
                array_unshift($a[$z], $new);
                $ptr['stats'][] = $a[$z];
            }
        }
        $array = array_merge_recursive((array)$array, $tmp);
        unset($a[$z]);
    }
    return $array;
}

示例结果..

Array
(
    [one] => Array
        (
            [two] => Array
                (
                    [three] => Array
                        (
                            [stats] => Array
                                (
                                    [0] => Array
                                        (
                                            [0] => win
                                            [1] => ner
                                        )

                                    [1] => Array
                                        (
                                            [0] => win
                                            [1] => dog
                                        )

                                    [2] => Array
                                        (
                                            [0] => lost
                                            [1] => cat
                                        )

                                )

                        )

                    [five] => Array
                        (
                            [stats] => Array
                                (
                                    [0] => Array
                                        (
                                            [0] => win
                                            [1] => ner
                                        )

                                    [1] => Array
                                        (
                                            [0] => lost
                                            [1] => ner
                                        )

                                )

                        )

                )

        )

)

这样,stats键上方的每个数组级别都将用作树形表样式表中的标题“分支”,这将用于生成。