Recreate array from flat (where child arrays store index of parent array) to multidimensional?

前端 未结 2 841
Happy的楠姐
Happy的楠姐 2021-01-14 20:53

I am trying to take a flat array and recreate it so that it\'s multidimensional. I\'ve been looking into array_combine and array_merge, but I\'m not sure that either of thos

相关标签:
2条回答
  • 2021-01-14 21:07

    Ok, I'm making some assumptions here:

    • Each element has only 1 parent, so the parents array will have only 1 tid
    • The array is sorted such that children will appear only after their parents
    • Top-level elmenets will have parent = 0

    Given that, try this code:

    $original = array ( ... your original array ... );
    $nested = array ();
    
    $n = count($original);
    for ($i = 0; $i < $n; ++$i)
    {
        $nested[$original[$i]->tid] = $original[$i];
        $nested[$original[$i]->tid]->children = array ();
    }
    
    while ($n-- && $current = $original[$n])
        if ($current->parents[0] != 0 && $current->parents[0] != $current->tid)
        {
            $nested[$current->parents[0]]->children[] = $current;
            unset ($nested[$current->tid]);
        }
    
    0 讨论(0)
  • 2021-01-14 21:12

    First off, what you are showing is not an multidimensional array, but an array of StdClass objects.

    If it's alright with you to make them truely arrays then this might do it:

    // initiate result array
    $multiArray = array();
    
    // assume $items is your current array
    foreach( $items as $item )
    {
        // cast StdClass to array
        $objToArray = (array) $item;
    
        // if this item is initiated already merge it with the current item
        $multiArray[ $objToArray[ 'tid' ] ] = isset( $multiArray[ $objToArray[ 'tid' ] ] ) ? $multiArray[ $objToArray[ 'tid' ] ] + $objToArray : $objToArray;
    
        foreach( $objToArray[ 'parents' ] as $parentId )
        {
            // if parents don't exist yet, initiate them
            if( !isset( $multiArray[ $parentId ] ) )
            {
                $multiArray[ $parentId ] = array(
                    'children' => array()
                );
            }
    
            // add this item to the parents children collection by reference (for efficiency)
            $multiArray[ $parentId ][ 'children' ][ $objToArray[ 'tid' ] ] = &$multiArray[ $objToArray[ 'tid' ] ];
        }
    }
    

    With this you can easily find items by id with:

    $item = $multiArray[ $someId ];
    

    And to get a child:

    $child = $item[ 'children' ][ $someChildId ];
    

    Or all children:

    $children = $item[ 'children' ];
    

    EDIT
    Ok, I've tested it now, and it seems to work fine after adding some missing semicolons.

    0 讨论(0)
提交回复
热议问题