<span style="font-size: 18px; font-family: Arial, Helvetica, sans-serif; background-color: rgb(255, 255, 255);">
</span>
<span style="font-size: 18px; font-family: Arial, Helvetica, sans-serif; background-color: rgb(255, 255, 255);"></span><pre code_snippet_id="495329" snippet_file_name="blog_20141024_1_8664932" name="code" class="csharp">對於二叉樹的遍歷循環一直覺得是自己的軟肋, 在網上看到許多一些交叉, 總覺得只是囫圇吞棗, 強行記住, 卻隱隱覺得自己沒有真正理解其中的真諦
於是特地抽出時間對二叉樹的遍歷用代碼實現了一遍, 找找手感。 二叉樹的前序遍歷, 和中序遍歷整體感覺上都挺好實現的, 後續遍歷由於需要兩次返回節點, 頗有挑戰性。
首先溫習一下後續遍歷的規則
public void Recurrence_travel(Bittree ptree)
{
if (ptree == null)
{
return;
}
Recurrence_travel(ptree.plefttree);
Recurrence_travel(ptree.prighttree);
Console.WriteLine(ptree.keyvalue.ToString());
}
二叉樹的循環實現:
public void Loop_travel(Bittree ptree)
{
if (ptree == null)
{
return;
}
Poststack treelist = new Poststack();
int counts=-1;
while (ptree != null || treelist.Get_size() != 0)
{
while (ptree != null)
{
if (ptree.plefttree == null && ptree.prighttree == null)
{
Console.WriteLine(ptree.keyvalue.ToString());
break; // jump out first loop
}
if (ptree.plefttree != null)
{
treelist.Push(ptree);
ptree = ptree.plefttree;
continue; //ship into next loop
}
if (ptree.plefttree==null && ptree.prighttree != null)
{
treelist.Push(ptree);
break;
}
}
ptree = treelist.Pop(ref counts);
if (counts == 0) // first time to get back
{
ptree = ptree.prighttree; // turn right to travel
continue;
}
if (counts == 1) // second time to get back
{
Console.WriteLine(ptree.keyvalue.ToString());
ptree = null; // ensure it would not enter second loop
}
}
}
輔助堆棧:
class Poststack
{
// second paramter could be counts for the pop out
private Dictionary<Bittree, int> treedict=new Dictionary<Bittree, int>();
public Poststack()
{
}
public void Push(Bittree ptree)
{
if (ptree == null)
{
return;
}
treedict.Add(ptree, 0);
}
public Bittree Pop(ref int pcounts)
{
if (treedict.Count() ==0)
{
return null;
}
Bittree tptree = treedict.Last().Key;
pcounts = treedict.Last().Value;
if (pcounts == 0)
{
treedict.Remove(tptree);
treedict.Add(tptree, pcounts + 1);
return tptree;
}
if (pcounts == 1) // second travel
{
treedict.Remove(tptree);
return tptree;
}
return null;
}
public int Get_size()
{
return treedict.Count();
}
}