說起那個無限級分類,相信很多人都知道是什麼東西,也曾經做過。我也相信,大家用得最多的實現方式就是做一個遞歸。
最近我也要做一個帶無限級分類的菜單,但是我又不想用遞歸來做,所以我需要用其他方式來實現,那就是迭代了。
首先,我需要定義一個實體模型,這舉一個省市無限級的例子:
class Loaction { public int ID { get; set; } public int PID { get; set; } public string Name { get; set; } //地方名 public int Level { get; set; } //深度 }
然後寫方法,這裡需要利用到棧的後進先出的特點:
public static List<Loaction> Soft(List<Loaction> data, int pid) { Stack task = new Stack(); task.Push(pid); List<Loaction> tree = new List<Loaction>(); int level = 0; while (task.Count > 0) { bool flag = false; for (int i = 0; i < data.Count; i++) { var l = data[i]; if (l.PID == pid) { pid = l.ID; task.Push(l.ID); l.Level = level; level++; tree.Add(l); data.Remove(l); i--; flag=true; } } if (!flag) { task.Pop(); if (task.Count > 0) { pid = Convert.ToInt32(task.Peek()); level--; } } } return tree; }
最後准備數據->調用->輸出:
static void Main(string[] args) { var data = new List<Loaction>(); data.Add(new Loaction() { ID = 1, PID = 0, Name = "北京" }); data.Add(new Loaction() { ID = 2, PID = 0, Name = "廣東" }); data.Add(new Loaction() { ID = 3, PID = 0, Name = "上海" }); data.Add(new Loaction() { ID = 4, PID = 0, Name = "重慶" }); data.Add(new Loaction() { ID = 5, PID = 0, Name = "黑龍江" }); data.Add(new Loaction() { ID = 6, PID = 1, Name = "豐台" }); data.Add(new Loaction() { ID = 7, PID = 1, Name = "海澱" }); data.Add(new Loaction() { ID = 8, PID = 1, Name = "石景山" }); data.Add(new Loaction() { ID = 9, PID = 3, Name = "上海市" }); data.Add(new Loaction() { ID = 10, PID = 2, Name = "廣州" }); data.Add(new Loaction() { ID = 11, PID = 5, Name = "齊齊哈爾" }); data.Add(new Loaction() { ID = 12, PID = 2, Name = "茂名" }); data.Add(new Loaction() { ID = 13, PID = 2, Name = "深圳" }); data.Add(new Loaction() { ID = 14, PID = 5, Name = "哈爾濱" }); data.Add(new Loaction() { ID = 15, PID = 4, Name = "重慶市" }); data.Add(new Loaction() { ID = 16, PID = 2, Name = "東莞" }); data.Add(new Loaction() { ID = 17, PID = 2, Name = "中山" }); data.Add(new Loaction() { ID = 18, PID = 16, Name = "厚街鎮" }); var tree = Soft(data, 0); foreach (var t in tree) { var sb = new StringBuilder(); for (int i = 0; i < t.Level; i++) { sb.Append(" "); } sb.Append(t.Name); Console.WriteLine(sb.ToString()); } Console.ReadKey(); }
然後效果如下:
就是這個樣子。。。。。(END)