C#高级:递归4-根据一颗树递归生成数据列表

一、目的

该程序展示了如何将树形结构的数据(例如家庭成员信息)转化为一维列表形式,以便于存储、展示或操作。

二、流程思路

  1. 创建树 :首先通过 GetDemoTree 创建一个简单的家庭树,树的根节点是"爸爸",然后通过父子关系组织出完整的树结构。
  2. 递归转换 :通过 GetListTree 方法,将该树结构转化为一维列表。在这个过程中,树的每个节点都会被递归遍历,并转换为 TreeList<PersonTree> 形式的条目,保存节点的层级信息(Level)和节点的详细数据(Data)。
  3. 结果 :最终生成的 listTree 是一个平坦的、按层级排列的列表,可以用于展示、处理或者进一步的分析。

三、代码展示

cs 复制代码
using System;
using System.Collections.Generic;

class PersonTree
{
    public int Id { get; set; }
    public int? ParentID { get; set; }
    public string Name { get; set; }

    public List<PersonTree> Children = new List<PersonTree>();
}

class TreeList<T> where T : class, new()
{
    /// <summary>
    /// 树ID(从T获取)
    /// </summary>
    public string Id { get; set; }
    /// <summary>
    /// 树的父级的ID(从T获取)
    /// </summary>
    public string PId { get; set; }
    /// <summary>
    /// 树的层级(从1开始)
    /// </summary>
    public int Level { get; set; }
    /// <summary>
    /// 树的对应节点的实体(如果数据量太大了,可以不写这个属性,把需要的属性例如Name放到外面去)
    /// </summary>
    public T Data { get; set; } = new T();
}

class Program
{
    static void Main()
    {
        //获取测试树:爸爸 - 我 妹妹 - 儿子 女儿
        var demoTree = GetDemoTree();

        //把树递归后转化为一维列表
        List<TreeList<PersonTree>> listTree = GetListTree(demoTree);
        ;
    }

    private static List<TreeList<PersonTree>> GetListTree(PersonTree demoTree, int level = 1)
    {
        List<TreeList<PersonTree>> output = new List<TreeList<PersonTree>>();

        // 每次递归都会new出output,因此不会反复添加根节点
        output.Add(new TreeList<PersonTree>
        {
            Id = demoTree.Id.ToString(),
            PId = demoTree.ParentID.ToString(),
            Level = level,
            Data = demoTree
        });

        // 如果有子节点,递归调用,增加层级
        if (demoTree.Children != null)
        {
            foreach (var item in demoTree.Children)
            {
                output.AddRange(GetListTree(item, level + 1));  // 递归调用时传递新的层级
            }
        }

        return output;
    }


    public static PersonTree GetDemoTree()
    {
        // 创建爸爸节点
        PersonTree dad = new PersonTree
        {
            Id = 1,
            Name = "爸爸",
            ParentID = null
        };

        // 创建我节点
        PersonTree me = new PersonTree
        {
            Id = 2,
            Name = "我",
            ParentID = dad.Id
        };

        // 创建妹妹节点
        PersonTree sister = new PersonTree
        {
            Id = 3,
            Name = "妹妹",
            ParentID = dad.Id
        };

        // 创建儿子节点
        PersonTree son = new PersonTree
        {
            Id = 4,
            Name = "儿子",
            ParentID = me.Id
        };

        // 创建女儿节点
        PersonTree daughter = new PersonTree
        {
            Id = 5,
            Name = "女儿",
            ParentID = me.Id
        };

        // 将儿子和女儿添加为我的子节点
        me.Children.Add(son);
        me.Children.Add(daughter);

        // 将我和妹妹添加为爸爸的子节点
        dad.Children.Add(me);
        dad.Children.Add(sister);
        return dad;
    }
}

【思考】假如PersonTree 没有 ParentID 这个字段 应该如何递归生成一维列表呢

【答案】递归方法多加一个Parent字段

cs 复制代码
private static List<TreeList<PersonTree>> GetListTree(PersonTree demoTree, int level = 1, string parentId = null)
{
    List<TreeList<PersonTree>> output = new List<TreeList<PersonTree>>();

    // 每次递归都会new出output,因此不会反复添加根节点
    output.Add(new TreeList<PersonTree>
    {
        Id = demoTree.Id.ToString(),
        PId = parentId,
        Level = level,
        Data = demoTree
    });

    // 如果有子节点,递归调用,增加层级
    if (demoTree.Children != null)
    {
        foreach (var item in demoTree.Children)
        {
            output.AddRange(GetListTree(item, level + 1, demoTree.Id.ToString()));  // 递归调用时传递新的父ID
        }
    }

    return output;
}
相关推荐
mi-key31 分钟前
键盘过滤驱动
windows·驱动开发·计算机外设·系统安全
秋の花2 小时前
【Java】List一部分常见问题
java·windows·list
菜到极致就是渣3 小时前
C#中的关键字out和ref的区别
开发语言·c#
乐茵安全3 小时前
《Windows基础与网络安全:用户账户管理与安全策略》
windows·安全·web安全
坐井观老天4 小时前
使用WPF在C#中制作下载按钮
开发语言·c#·wpf
CodeCraft Studio4 小时前
【实用技能】如何使用 .NET C# 中的 Azure Key Vault 中的 PFX 证书对 PDF 文档进行签名
c#·.net·azure
奔跑的犀牛先生4 小时前
unity学习14:unity里的C#脚本的几个基本生命周期方法, 脚本次序order等
学习·unity·c#
程序猿张同学6 小时前
window CMD大全
windows·经验分享·自动化
数据的世界016 小时前
C#标识符和关键字
java·服务器·c#
鲤籽鲲8 小时前
C# 整型、浮点型 数值范围原理分析
开发语言·c#