如何用C#/.NET将N叉目录树转换为带路径的文件夹文件列表
N叉树文件夹-文件结构转换为路径关联文件列表
我有一个N叉树结构,节点分为**文件夹(Folder)和文件(File,叶子节点)**两种类型。文件夹节点可以包含子文件夹或文件节点。需要将该结构转换为一个列表,每个条目包含从根到目标文件夹的复合路径,以及该文件夹下的所有文件节点。
示例结构
- Root
- Folder1
- File1
- File2
- Folder2
- Folder3
- File3
- File4
- Folder3
- Folder1
期望转换结果
- Folder1 - File1, File2
- Folder2.Folder3 - File3
- Folder2 - File4
初始节点结构代码
public interface INode { } public class Folder : INode { public string Name { get; set; } public List<INode>? Children { get; set; } } public class File : INode { public string Name { get; set; } } var tree = new Folder() { Name = "Root" }; var folder1 = new Folder() { Name = "Folder1" }; var file1 = new TreeConverter.File() { Name = "File1" }; var file2 = new TreeConverter.File() { Name = "File2" }; folder1.Children = new List<INode> { file1, file2 }; var folder2 = new Folder() { Name = "Folder2" }; var folder3 = new Folder() { Name = "Folder3" }; var file3 = new TreeConverter.File() { Name = "File3" }; var file4 = new TreeConverter.File() { Name = "File4" }; folder3.Children = new List<INode> { file3 }; folder2.Children = new List<INode>() { folder3, file4 }; tree.Children = new List<INode>() { folder1, folder2 }; List<Folder> folders = ConvertTreeToListofFoldersWithEachEntryNamedRootToLastFolderWithAllContainingFileNodes(tree); // 返回的folders中每个文件夹的路径名称应为:[Folder1, Folder2.Folder3, Folder2] // 可通过遍历每个节点的子节点获取对应的文件节点
简化节点结构后的解决方案
我后来简化了节点结构,通过统一的Node类结合枚举区分类型,实现了需求,代码如下:
public enum NodeType { Folder, File } public class Node { public string Name { get; set; } public List<Node> Children { get; set;} public NodeType Type { get; set; } public Node(string name, NodeType type) { this.Name = name; this.Type = type; this.Children = new List<Node>(); } } // 构建树结构 var tree = new Node("Root", NodeType.Folder); var folder1 = new Node("Folder1", NodeType.Folder ); var file1 = new Node ("File1", NodeType.File ); var file2 = new Node ("File2", NodeType.File ); var file3 = new Node ("File3", NodeType.File ); var file4 = new Node ("File4", NodeType.File ); var folder2 = new Node ("Folder2", NodeType.Folder ); var folder3 = new Node ("Folder3", NodeType.Folder ); folder1.Children = new List<Node> { file1, file2 }; folder3.Children = new List<Node> { file3 }; folder2.Children = new List<Node>() { folder3, file4 }; tree.Children = new List<Node>() { folder1, folder2 }; // 执行转换 var foldersWithFiles = GetFoldersWithFiles(tree); foreach(var folder in foldersWithFiles) { Console.WriteLine($"文件夹: {folder.Key}"); Console.WriteLine($" 文件: {string.Join(",", folder.Value)}"); } Dictionary<string, List<string>> GetFoldersWithFiles(Node root) { var foldersWithFiles = new Dictionary<string, List<string>>(); Traverse(root, root.Name, foldersWithFiles); return foldersWithFiles; } void Traverse(Node node, string path, Dictionary<string, List<string>> foldersWithFiles) { // 获取当前节点下的所有文件子节点 var childFiles = node.Children.Where(child => child.Type == NodeType.File); if (childFiles.Any()) { foldersWithFiles[path] = childFiles.Select(child => child.Name).ToList(); } // 递归遍历所有子文件夹节点 foreach (var child in node.Children.Where(child => child.Type == NodeType.Folder)) { Traverse(child, $"{path}/{child.Name}", foldersWithFiles); } }
运行输出
文件夹: Root/Folder1 文件: File1,File2 文件夹: Root/Folder2 文件: File4 文件夹: Root/Folder2/Folder3 文件: File3
内容的提问来源于stack exchange,提问作者Heems
相关产品推荐
相关产品推荐

