題解 求後序遍歷(二叉樹遍歷,遞迴)

2021-10-05 02:29:31 字數 2539 閱讀 7580

【題目描述】

給出二叉樹的先序遍歷和中序遍歷,求後序遍歷。

【輸入】

輸入共兩行,第一行乙個字串,表示樹的先序遍歷,第二行乙個字串,表示樹的中序遍歷。樹的結點一律用小寫字母表示。字串長度小於100

10010

0。【輸出】

輸出僅一行,表示樹的後序遍歷序列。

【樣例輸入】

abdec

dbeac

【樣例輸出】

debca
二叉樹有三種遍歷方法:

先序遍歷:(1)訪問根節點;(2)先序遍歷左子樹;(3)先序遍歷右子樹。

中序遍歷:(1)中序遍歷左子樹;(2)訪問根節點;(3)中序遍歷右子樹。

後序遍歷:(1)後序遍歷左子樹;(2)後序遍歷右子樹;(3)訪問根節點。

已知先序遍歷和中序遍歷:

對於先序遍歷,第乙個結點為根節點a

aa。接下來找出中序遍歷的根結點,根據中序遍歷的順序,可以知道,根節點a

aa左邊為a

aa的左子樹,右邊為a

aa的右子樹:

對於先序遍歷,根節點a

aa後緊跟的為a

aa的左子樹,左子樹訪問完之後為a

aa的右子樹。可以知道,a

aa的左子樹的結點數目是固定的,那麼可以通過中序遍歷根節點a

aa左邊的結點數目,即左子樹的結點總數,從而在先序遍歷中找到左子樹的區間,對於樣例,先序遍歷中,根節點a

aa後3

33個結點為a

aa的左子樹,剩下的為右子樹。

因此左子樹的先序遍歷為:bde

bdebd

e,左子樹的中序遍歷為:dbe

dbedb

e;右子樹的先序遍歷為:c

cc,左子樹的中序遍歷為:ccc;

根結點為aaa。

按照同樣的方法,繼續對左右子樹進行拆分。

假設先序遍歷的下標區間為l

1l_1

l1​~r

1r_1

r1​,中序遍歷的下標區間為l

先序的第乙個結點s1[

l1]s_1[l_1]

s1​[l1

​]為根,在中序遍歷s

2s_2

s2​中找到結點s1[

l1]s_1[l_1]

s1​[l1

​],設位置為mmm。

中序遍歷中,根的左子樹在中序的位置下標為為l

2l_2

l2​~ m−1

m-1m−

1,右子樹為m+1

m+1m+

1~ r

2r_2

r2​。

先序訪問根結點後緊跟訪問左子樹,之後為右子樹

因此,中序遍歷的左子樹下標l

2l_2

l2​~ m−1

m-1m−

1總共(m−l

2m-l_2

m−l2

​)個結點,對應先序遍歷的l1+

1l_1+1

l1​+

1開始的(m−l

2m-l_2

m−l2

​)結點,即先序遍歷的左子樹下標區間為l1+

1l_1+1

l1​+

1 ~ l1+

m−l2

l_1+m-l_2

l1​+m−

l2​中序遍歷的右子樹區間m+1

m+1m+

1~ r

2r_2

r2​對應先序的右子樹區間l1+

m+l2

+1l_1+m+l_2+1

l1​+m+

l2​+

1 ~ r

1r_1

r1​根據後序遍歷的訪問順序,左右子樹遍歷完畢,就可以輸出根結點s1[

//先序遍歷x1~y1,對應中序遍歷x2~y2

intmain()

演算法求二叉樹後序遍歷

演算法原題來自 hihocoder 題目要求使用樹的前序遍歷和中序遍歷求出樹的後序遍歷串。那麼我們想到的方法便是根據前序遍歷和中序遍歷求出這棵樹,那麼就可以很容易的後序遍歷此樹了。根據題目我們先來定義樹節點的資料結構 typedef struct nodenode t 那麼我們可以這樣設定這個函式 ...

二叉樹非遞迴後序遍歷

注釋 後序非遞迴遍歷的難處就在,最右結點無法直接找到後繼結點,後序線索化二叉樹在這裡就不能使用遞迴了,其實知道了遞迴的運作過程就不難理解為何不能用遞迴後序線索化了遞迴詳細執行過程a b c d e f h 當遍歷到最左邊的時候,d沒有左右結點了,輸出d,需要返回b去遍歷b的右子樹,e沒有左右結點e輸...

後序非遞迴遍歷二叉樹

後序遍歷的非遞迴演算法中節點的進棧次數是兩個,即每個節點都要進棧兩次,第二次退棧的時候才訪問節點。第一次進棧時,在遍歷左子樹的過程中將 根 節點進棧,待左子樹訪問完後,回溯的節點退棧,即退出這個 根 節點,但不能立即訪問,只能借助於這個 根 去找該 根 的右子樹,並遍歷這棵右子樹,直到該右子樹全部遍...