日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

程序基本功之遍历二叉树

發布時間:2025/6/15 编程问答 12 豆豆
生活随笔 收集整理的這篇文章主要介紹了 程序基本功之遍历二叉树 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

最近工作忙,沒時間思考復雜的問題了。正好要招人就得有面試的嘛,自己也溫習一下,要不然怎么去問別人。

今天復習一下二叉樹的遍歷,前序(pre-order,NLR)、中序(in-order,LNR)、后序(post-order,LRN)、層序(level-order),用和不用遞歸。

概念就不用多解釋了,前、中、后是指根結點的訪問時機,在左、右子樹之前、中間、或之后。層序就是從根結點開始從上至下、從左到右地依次訪問。

一棵二叉樹

如上圖所示的一棵二叉樹,對應的遍歷結果分別是:

  • 前序(NLR):A B D C E G H F I
  • 中序(LNR):D B A G E H C F I
  • 后序(LRN):D B G H E I F C A
  • 層序:A B C D E F G H I

一、用遞歸處理二叉樹的前序、中序和后序遍歷

遞歸真是一個迷人東西,它可以把復雜的邏輯變得異常簡潔,這也是自然界的表現形式之一。基于遞歸的前、中、后序遍歷二叉樹的程序幾乎完全相同,用兩個遞歸調用分別處理左、右子樹,剩下的事情就是打印根結點。為節省篇幅,直接把三個程序寫在一起,用一個參數來控制是哪種遍歷方式,也可以更方便地看出三者之間的區別。

1 2 3 4 5 6 7 def VisitTree_Recursive(root, order):if root:if order == 'NLR': print(root.data)VisitTree_Recursive(root.left, order)if order == 'LNR': print(root.data)VisitTree_Recursive(root.right, order)if order == 'LRN': print(root.data)

二、非遞歸的前序、中序遍歷

如果不用遞歸呢?實際上我們要做的就是自己維護一個棧(數據結構)來保存需要但尚未來得及處理的數據。

前序和中序都是非常簡單的,當遇到一個非空的根結點時,打印其數據(如果是前序遍歷),并將其壓棧,然后遞歸地(這里用循環來模擬遞歸)處理其左子結點;當沒有左子結點時,從棧中彈出之前遇到的某個根結點(它沒有左子結點,或者左子結點已經處理完畢,需要再處理右子結點),打印數據(如果是中序遍歷),然后繼續處理右子結點。同樣地,把兩種遍歷方式寫在一起以便比較。

123456789 10 11 def VisitTree(root, order):s = []while root or s:if root:if order == 'NLR': print(root.data)s.append(root)root = root.leftelse:root = s.pop()if order == 'LNR': print(root.data)root = root.right

三、非遞歸的后序遍歷

后序遍歷要稍微復雜一點點,在前序和中序遍歷的程序中,當我們準備進入根結點的右子樹時,根結點就被扔出棧外了。但在后序遍歷時,我們仍需保留它,直到右子樹處理完畢。

首先想到的改動就是在上面的程序的第9行到11行,不要從棧s中將根結點彈出,而是直接開始處理右子結點。但這就會帶來一個問題:什么時候彈出根結點?實際上當左子樹遍歷完成、或者右子樹遍歷完成時,我們都會在棧里看到根結點,為了區分這兩種狀態,添加一個臨時變量記錄前一次訪問的結點,如果前一個結點是根結點的右子樹,就說明左右子樹全都遍歷完成了。非常簡單。

123456789 10 11 12 13 def VisitTreeLRN(root):s = []pre = Nonewhile root or s:if root:s.append(root)root = root.leftelif s[-1].right != pre:root = s[-1].rightpre = Noneelse:pre = s.pop()print(pre.data)

四、非遞歸的層序遍歷

層序遍歷可以寫成遞歸嗎?還真沒研究過。非遞歸的時候,層序遍歷使用的是隊列,而非棧。

處理過程非常簡明,遇到一個結點,打印信息,然后依次將左、右子結點加入隊列等待后續處理。

123456789 10 from collections import dequedef VisitTree_LevelOrder(root):if not root: returnq = deque([root])while q:root = q.popleft()print(root.data)if root.left: q.append(root.left)if root.right: q.append(root.right)

附錄

上面的python代碼基于v2.7。另外可以用下面這段代碼來定義最簡單的二叉樹結點類,生成最上面圖示的二叉樹:

123456789 10 11 12 13 14 15 16 class Node:def __init__(self, data, left = None, right = None):self.data = dataself.left = leftself.right = rightg = Node('G') h = Node('H') e = Node('E', g, h) i = Node('I') f = Node('F', None, i) c = Node('C', e, f) d = Node('D') b = Node('B', d) a = Node('A', b, c) root = a

總結

以上是生活随笔為你收集整理的程序基本功之遍历二叉树的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 久久久午夜精品福利内容 | 91微拍 | 东北少妇露脸无套对白 | 少妇视频一区二区三区 | 成人羞羞网站 | av中文字幕亚洲 | 色呦| 色91在线 | 青苹果av | 鲁大师私人影院在线观看 | www.久久99 | 爽爽影院在线免费观看 | 国产精品一品二区三区的使用体验 | 五月天激情婷婷 | 午夜dv内射一区二区 | 大地资源二中文在线影视观看 | av一本在线 | 免费黄色大片 | 欧美成人a∨高清免费观看 国产精品999视频 | 国产香蕉视频在线观看 | 高清在线一区二区 | 久久久精品视频一区 | 欧美精品欧美极品欧美激情 | 美足av电影 | 国产第九页 | 在线免费视频一区 | 极品少妇一区 | 伊人免费在线观看高清版 | 九九久久国产精品 | 日本a∨视频 | 97免费视频观看 | 亚洲欧美日韩综合在线 | 97精品久久久 | 92国产精品 | 久久久观看| 日韩欧美国产视频 | 123毛片| 久久欧 | 99热国产精品| 三级网站 | 国产视频在线观看一区 | 中文字幕国产亚洲 | 日日干视频 | 黄色成人av | 欧美日韩精品一区二区 | 91香蕉视频在线观看免费 | 三级av| 国产区欧美区日韩区 | www国产精品内射老熟女 | 亚洲喷潮| 亚洲欧美日韩一区二区三区四区 | 色资源在线 | 色蜜桃av| 国产电影一区二区三区爱妃记 | 久久精品国产99国产 | 亚洲吧| 可以免费观看的av网站 | 亚洲熟妇毛茸茸 | 91成人高清 | 懂色av蜜臂av粉嫩av | 第九色激情 | 日本阿v视频在线观看 | 福利在线影院 | 亚洲成人99 | 国产一级片免费在线观看 | 捆绑裸体绳奴bdsm亚洲 | 小小姑娘电影大全免费播放 | 精品97人妻无码中文永久在线 | 久久99精品久久久 | 狠狠躁18三区二区一区视频 | 国产片久久 | 伊人成年综合网 | 女人私密又肥又大 | avtt中文字幕| 丝袜一区二区三区 | 神马午夜51| 午夜精品福利视频 | 中国性xxx| 国模吧一区二区三区 | 综合五月| 国产黄色精品视频 | 蜜臀av在线播放 | 成人免费毛片视频 | 国产精品毛片久久久久久久 | 欧美首页| 国内精品久久久久久久影视简单 | 污视频导航 | wwwww国产| 91精品久久香蕉国产线看观看 | 国产日韩欧美二区 | 日韩精品美女 | 欧美性爱精品在线 | 国产在线一二 | 日韩成人在线免费视频 | 欧美影音 | 国产午夜在线播放 | 国产亚洲激情 | 琪琪色av | 噜噜噜噜噜色 |