How can I build a nested HTML list with an infinite depth from a flat array?

前端 未结 3 905
暗喜
暗喜 2021-01-06 10:00

I\'m trying to produce a multi-level HTML list from a source array that is formatted like this:

/**
 * id = unique id
 * parent_id = \"id\" that this item is         


        
相关标签:
3条回答
  • 2021-01-06 10:17

    Print:

    function printListRecursive(&$list,$parent=0){
        $foundSome = false;
        for( $i=0,$c=count($list);$i<$c;$i++ ){
            if( $list[$i]['parent_id']==$parent ){
                if( $foundSome==false ){
                    echo '<ul>';
                    $foundSome = true;
                }
                echo '<li>'.$list[$i]['text'].'</li>';
                printListRecursive($list,$list[$i]['id']);
            }
        }
        if( $foundSome ){
            echo '</ul>';
        }
    }
    
    printListRecursive($list);
    

    Create multidimensional array:

    function makeListRecursive(&$list,$parent=0){
        $result = array();
        for( $i=0,$c=count($list);$i<$c;$i++ ){
            if( $list[$i]['parent_id']==$parent ){
                $list[$i]['childs'] = makeListRecursive($list,$list[$i]['id']);
                $result[] = $list[$i];
            }
        }
        return $result;
    }
    
    $result = array();
    $result = makeListRecursive($list);
    echo '<pre>';
    var_dump($result);
    echo '</pre>';
    
    0 讨论(0)
  • 2021-01-06 10:30

    Tested and working :)

    $list = array(...);
    $nested = array();
    
    foreach ($list as $item)
    {
        if ($item['parent_id'] == 0)
        {
            // Woot, easy - top level
            $nested[$item['id']] = $item;
        }
        else
        {
            // Not top level, find it's place
            process($item, $nested);
        }
    }
    
    // Recursive function
    function process($item, &$arr)
    {
        if (is_array($arr))
        {
            foreach ($arr as $key => $parent_item)
            {
                // Match?
                if (isset($parent_item['id']) && $parent_item['id'] == $item['parent_id'])
                {
                    $arr[$key]['children'][$item['id']] = $item;
                }
                else
                {
                    // Keep looking, recursively
                    process($item, $arr[$key]);
                }
            }
        }
    }
    
    0 讨论(0)
  • 2021-01-06 10:38

    Some methods I recently wrote, maybe some will help, sorry I'm short on time and cannot rewite them to match your needs.

    This code is actually a part of Kohana Framework Model, method ->as_array() is used to flat an Database_Result object.

    function array_tree($all_nodes){
        $tree = array();
        foreach($all_nodes as $node){
            $tree[$node->id]['fields'] = $node->as_array();
            $tree[$node->id]['children'] = array();
    
            if($node->parent_id){
                 $tree[$node->parent_id]['children'][$node->id] =& $tree[$node->id];
            }
        }
    
    
        $return_tree = array();
        foreach($tree as $node){
            if($node['fields']['depth'] == 0){
                $return_tree[$node['fields']['id']] = $node;
            }
        }
    
        return $return_tree;
    }
    

    array_tree() is used to make a tree out of a flat array. The key feature is the =& part ;)

    function html_tree($tree_array = null){
            if( ! $tree_array){
               $tree_array = $this -> array_tree();
            }
    
            $html_tree = '<ul>'."\n";
            foreach($tree_array as $node){
                $html_tree .= $this->html_tree_crawl($node);
            }
            $html_tree .= '</ul>'."\n";
    
    
            return $html_tree;
        }
    
    function html_tree_crawl($node){
            $children = null;
    
            if(count($node['children']) > 0){
                $children = '<ul>'."\n";
                foreach($node['children'] as $chnode){
                    $children .= $this->html_tree_crawl($chnode);
                }
                $children .= '</ul>'."\n";
            }
    
            return $this->html_tree_node($node, $children);
        }
    

    html_tree_node() is a simple method to display current node and children in HTML. Example below:

    <li id="node-<?= $node['id'] ?>">
        <a href="#"><?= $node['title'] ?></a>
        <?= (isset($children) && $children != null) ? $children : '' ?>
    </li>
    
    0 讨论(0)
提交回复
热议问题