再帰クエリで根付き木
再帰クエリで根付き木を解くコード。
using System.Collections.Generic; using System.Linq; namespace RootedTree { class Program { static void Main(string[] args) { // NodeId,ParentNodeId string[,] src = new string[9,2]{ {"A101", ""}, {"A201", "A101"}, {"A202", "A101"}, {"A301", "A201"}, {"A302", "A201"}, {"A303", "A201"}, {"A304", "A201"}, {"A401", "A302"}, {"A402", "A304"}, }; // Setに全てのNode情報を格納 HashSet<Node> nodeSet = new HashSet<Node>(); for (int i = 0; i < src.GetLength(0) ;i++) { Node node = new Node(); node.NodeId = src[i, 0]; node.ParentNodeId = src[i, 1]; nodeSet.Add(node); } // 最上位のノードを探す var startNode = nodeSet .Where(e => "".Equals(e.ParentNodeId)) .Select(e => e) .First(); // 最上位から探索開始 search(nodeSet, startNode, 0); System.Console.WriteLine(); } /// <summary> /// 子のノードを探す /// </summary> /// <param name="nodeSet">全てのノードのSet</param> /// <param name="startNode">始点ノード</param> /// <param name="depth">階層の深さ</param> private static void search(HashSet<Node> nodeSet, Node startNode, int depth) { System.Console.WriteLine(new string(' ', depth) + startNode.NodeId); // 始点ノードの子ノードを取得する var childNodes = nodeSet .Where(e => startNode.NodeId.Equals(e.ParentNodeId)) .Select(e => e); if (childNodes.Count() > 0) { // 子ノードがある場合 foreach (Node child in childNodes) { // 子ノードの更に下を探索 search(nodeSet, child, depth + 1); } } System.Console.WriteLine(new string('-', depth) + startNode.NodeId); } } /// <summary> /// ノードを表すクラス /// </summary> class Node { public string NodeId; public string ParentNodeId; } }
結果
A101
-A201
--A301
==A301
--A302
---A401
===A401
==A302
--A303
==A303
--A304
---A402
===A402
==A304
=A201
-A202
=A202
A101