将类似表的数组转换为类似树的数组


Converting table-like array to a tree-like array

考虑以下示例:

function tableToTree($array, $parents)
{
    $result = [];
    $p = $parents;
    foreach ($array as $k => $row) {
        $result[$row[$p[0]]][$row[$p[1]]]= $row[$p[2]]; // **
    }
    return $result;
}
$foo = [
    ['x' => 'a', 'y' => 'n','z'=>'AA'],
    ['x' => 'a', 'y' => 'm','z'=>'BB'],
    ['x' => 'b', 'y' => 'v','z'=>'CC'],
    ['x' => 'b', 'y' => 'w','z'=>'DD'],
];
print_r(tableToTree($foo, ['x', 'y','z']));

哪个收益率:

Array
(
    [a] => Array
        (
            [n] => AA
            [m] => BB
        )
    [b] => Array
        (
            [v] => CC
            [w] => DD
        )
)

以上代码仅在只有两个父级的情况下有效。如何重写由**表示的行,使其与任意数量的父级一起工作。

function tableToTree($array, $parent)
{
    $result = array();
    foreach ($array as $row) {
        $r = &$result;                                    // pointer to result
        $p = $parent;                                     // temporary copy of parents
        while(count($p) > 2) {                            // until last key and value
           $i = array_shift($p);                          // next key
           if(!isset($r[$row[$i]])) $r[$row[$i]] = null;  // add level
           $r = &$r[$row[$i]];                            // shift pointer to new level
        }
        $r[$row[array_shift($p)]] = $row[array_shift($p)]; // set value
    }
    return $result;
}
$foo = array(
    array('N' => 2, 'x' => 'a', 'y' => 'n','z'=>'AA'),
    array('N' => 1, 'x' => 'a', 'y' => 'm','z'=>'BB'),
    array('N' => 2, 'x' => 'b', 'y' => 'v','z'=>'CC'),
    array('N' => 1, 'x' => 'b', 'y' => 'w','z'=>'DD'),
    array('N' => 1, 'x' => 'c', 'y' => 'w','z'=>'DD'));
print_r(tableToTree($foo, array('N','x', 'y','z')));

结果

array (
  2 => array (
    'a' =>  array ( 'n' => 'AA',),
    'b' =>  array ( 'v' => 'CC',),
  ),
  1 =>  array (
    'a' => array ( 'm' => 'BB', ),
    'b' =>  array ( 'w' => 'DD', ),
    'c' =>  array ( 'w' => 'DD', ),
  ),
)