国产精品电影_久久视频免费_欧美日韩国产激情_成年人视频免费在线播放_日本久久亚洲电影_久久都是精品_66av99_九色精品美女在线_蜜臀a∨国产成人精品_冲田杏梨av在线_欧美精品在线一区二区三区_麻豆mv在线看

二叉樹迭代器算法

開發 后端 算法
二叉樹(Binary Tree)的前序、中序和后續遍歷是算法和數據結構中的基本問題,基于遞歸的二叉樹遍歷算法更是遞歸的經典應用。

二叉樹(Binary Tree)的前序、中序和后續遍歷是算法和數據結構中的基本問題,基于遞歸的二叉樹遍歷算法更是遞歸的經典應用。

假設二叉樹結點定義如下:

  1. struct Node { 
  2.     int value; 
  3.     Node *left; 
  4.     Node *right; 

 

  1. void inorder_traverse(Node *node) { 
  2.     if (NULL != node->left) { 
  3.         inorder_traverse(node->left); 
  4.     } 
  5.     do_something(node); 
  6.     if (NULL != node->right) { 
  7.         inorder_traverse(node->right); 
  8.     } 
  9.  

前序和后序遍歷算法類似。

但是,僅有遍歷算法是不夠的,在許多應用中,我們還需要對遍歷本身進行抽象。假如有一個求和的函數sum,我們希望它能應用于鏈表,數組,二叉樹等等不同的數據結構。這時,我們可以抽象出迭代器(Iterator)的概念,通過迭代器把算法和數據結構解耦了,使得通用算法能應用于不同類型的數據結構。我們可以把sum函數定義為:

  1. int sum(Iterator it) 

鏈表作為一種線性結構,它的迭代器實現非常簡單和直觀,而二叉樹的迭代器實現則不那么容易,我們不能直接將遞歸遍歷轉換為迭代器。究其原因,這是因為二叉 樹遞歸遍歷過程是編譯器在調用棧上自動進行的,程序員對這個過程缺乏足夠的控制。既然如此,那么我們如果可以自己來控制整個調用棧的進棧和出棧不是就達到 控制的目的了嗎?我們先來看看二叉樹遍歷的非遞歸算法:

  1. void inorder_traverse_nonrecursive(Node *node) { 
  2.     Stack stack; 
  3.     do { 
  4.         // node代表當前準備處理的子樹,層層向下把左孩子壓棧,對應遞歸算法的左子樹遞歸 
  5.         while (NULL != node) { 
  6.             stack.push(node); 
  7.             node = node->left; 
  8.         } 
  9.         do { 
  10.             Node *top = stack.top(); 
  11.             stack.pop(); //彈出棧頂,對應遞歸算法的函數返回 
  12.             do_something(top); 
  13.             if (NULL != top->right) { 
  14.                 node = top->right; //將當前子樹置為剛剛遍歷過的結點的右孩子,對應遞歸算法的右子樹遞歸 
  15.                 break
  16.             } 
  17.         } 
  18.         while (!stack.empty()); 
  19.     } 
  20.     while (!stack.empty()); 

通過基于棧的非遞歸算法我們獲得了對于遍歷過程的控制,下面我們考慮如何將其封裝為迭代器呢? 這里關鍵在于理解遍歷的過程是由棧的狀態來表示的,所以顯然迭代器內部應該包含一個棧結構,每次迭代的過程就是對棧的操作。假設迭代器的接口為:

  1. class Iterator { 
  2.     public
  3.         virtual Node* next() = 0; 
  4. }; 

下面是一個二叉樹中序遍歷迭代器的實現:

  1. class InorderIterator : public Iterator { 
  2.     public
  3.         InorderIterator(Node *node) { 
  4.             Node *current = node; 
  5.             while (NULL != current) { 
  6.                 mStack.push(current); 
  7.                 current = current->left; 
  8.             } 
  9.         } 
  10.         virtual Node* next() { 
  11.             if (mStack.empty()) { 
  12.                 return NULL; 
  13.             } 
  14.             Node *top = mStack.top(); 
  15.             mStack.pop(); 
  16.             if (NULL != top->right) { 
  17.                 Node *current = top->right; 
  18.                 while (NULL != current) { 
  19.                     mStack.push(current); 
  20.                     current = current->left; 
  21.                 } 
  22.             } 
  23.             return top; 
  24.          } 
  25.     private
  26.         std::stack<Node*> mStack; 
  27. }; 

下面我們再來考察一下這個迭代器實現的時間和空間復雜度。很顯然,由于棧中最多需要保存所有的結點,所以其空間復雜度是O(n)的。那么時間復雜度 呢?一次next()調用也最多會進行n次棧操作,而整個遍歷過程需要調用n次next(),那么是不是整個迭代器的時間復雜度就是O(n^2)呢?答案 是否定的!因為每個結點只會進棧和出棧一次,所以整個迭代過程的時間復雜度依然為O(n)。其實,這和遞歸遍歷的時空復雜度完全一樣。

除了上面顯式利用棧控制代碼執行順序外,在支持yield語義的語言(C#, Python等)中,還有更為直接的做法。下面基于yield的二叉樹中序遍歷的Python實現:

  1. // Python 
  2. def inorder(t): 
  3.     if t: 
  4.         for x in inorder(t.left): 
  5.             yield x 
  6.         yield t.label 
  7.         for x in inorder(t.right): 
  8.             yield x 

yield與return區別的一種通俗解釋是yield返回時系統會保留函數調用的狀態,下次該函數被調用時會接著從上次的執行點繼續執行,這是一種與 棧語義所完全不同的流程控制語義。我們知道Python的解釋器是C寫的,但是C并不支持yield語義,那么解釋器是如何做到對yield的支持的呢? 有了上面把遞歸遍歷變換為迭代遍歷的經驗,相信你已經猜到Python解釋器一定是對yield代碼進行了某種變換。如果你已經能夠實現遞歸變非遞歸,不 妨嘗試一下能否寫一段編譯程序將yield代碼變換為非yield代碼。

原文鏈接:http://coolshell.cn/articles/9886.html

責任編輯:陳四芳 來源: 酷殼網
相關推薦

2021-09-29 10:19:00

算法平衡二叉樹

2020-04-27 07:05:58

二叉樹左子樹右子樹

2020-09-23 18:25:40

算法二叉樹多叉樹

2021-09-15 07:56:32

二叉樹層次遍歷

2020-12-22 08:56:51

JavaScript數據結構前端

2009-08-11 13:29:57

C#二叉樹遍歷

2021-09-28 06:28:51

二叉樹公共祖先

2020-12-30 08:35:34

貪心算法監控

2021-04-19 07:47:42

數據結構二叉樹Tree

2021-04-20 08:37:14

數據結構二叉樹

2021-03-17 08:19:22

二叉樹LeetCode

2021-04-28 20:12:27

數據結構創建

2021-03-22 08:23:29

LeetCode二叉樹節點

2021-08-27 11:36:44

二叉樹回溯節點

2023-05-08 15:57:16

二叉樹數據結構

2020-11-02 09:15:47

算法與數據結構

2021-05-06 17:46:30

二叉樹數據結構

2022-10-26 23:58:02

二叉樹數組算法

2021-07-16 08:57:31

迭代遍歷二叉樹

2021-12-17 14:26:58

二叉樹節點數量
點贊
收藏

51CTO技術棧公眾號

国产伦精品一区二区三区千人斩| 蜜乳av一区二区| 久久一区中文字幕| 亚洲a中文字幕| 色av男人的天堂免费在线| 亚洲精品在线观看91| 亚洲视频在线一区二区| 久久精品91久久久久久再现| 黄色仓库视频网站| 成人免费av| 国产欧美一区二区三区鸳鸯浴| 国产不卡视频在线播放| 日韩欧美国产一区二区三区| 亚洲欧美日韩中文视频| 国产第一页在线| 成人精品亚洲人成在线| 国产美女精品视频免费播放软件| 1024成人| 日韩精品亚洲元码| 精品国产日本| 91精品国产91久久久久游泳池| 精品一区二区在线看| 成人免费大片黄在线播放| 麻豆av在线播放| 国产精品视频免费| 免费福利片在线观看| 国产一区二区欧美| 成人国产精品久久久| 99在线精品免费视频九九视 | 国产精品456露脸| 亚洲一区二区欧美激情| 男女羞羞电影免费观看| 国产成人综合自拍| 久久久久久久久影视| 亚洲美女毛片| 久久久精品视频成人| av中文字幕在线观看第一页 | 久久精品亚洲一区二区| 中文在线日韩| 亚洲高清免费在线| 亚洲人体一区| 成人黄色网址| 久久久久久久免费视频了| 久久99精品视频一区97| 97人人在线视频| 日韩国产欧美精品一区二区三区| 国产在线1区| 国产亚洲综合久久| 高清精品久久| 伊人久久男人天堂| 一区二区三区国产好| 日本久久久久久久| 亚久久调教视频| 5566成人精品视频免费| 成人黄色毛片| 亚洲图片激情小说| 极品美乳网红视频免费在线观看| 成人av手机在线观看| 亚洲av综合色区| 亚洲电影在线| 久久久久久久久久久福利| 中文字幕在线不卡国产视频| 日本视频在线| 国内成人精品一区| 久久久久久美女精品| 国产精品高清免费在线观看| 日韩精品网站| 7777精品久久久大香线蕉小说| 午夜精品福利影院| 免费久久一级欧美特大黄| 国产欧美一区二区三区网站| 在线免费av网站| 精品国产凹凸成av人网站| 亚洲国产精品一区在线观看不卡| 最新日韩欧美| 欧美日韩一区二区在线观看视频 | 97视频com| 一区二区动漫| 午夜视频你懂的| 欧美酷刑日本凌虐凌虐| 在线亚洲a色| 国产精品色悠悠| 成人午夜视频福利| 免费网站看v片在线a| 97视频在线观看成人| 国产伦精品一区二区三区免费| 国产va免费精品高清在线观看| 激情一区二区| 草裙成人精品一区二区三区 | 午夜激情影院| 免费99精品国产自在在线| 国产精品一级黄| 成人自拍视频网| 台湾十八成人网| 国产精品久久久久久久app| 午夜精品久久久久影视| 日韩在线中文| 国产裸舞福利在线视频合集| 国产91在线播放九色快色| 要久久电视剧全集免费| 久久久精品麻豆| 国产精品嫩草影院一区二区| 亚洲男同性视频| 午夜精品久久久久99热蜜桃导演 | av漫画网站在线观看| 亚洲精品电影在线一区| 日韩一区二区免费高清| 羞羞视频在线观看欧美| 亚洲精品毛片| 免费黄色在线网站| 可以免费在线看黄的网站| 亚洲精品免费av| 色美美综合视频| 日韩精品免费专区| 亚洲同志男男gay1069网站| 精品无人区一区二区三区| 91麻豆精品国产91久久久久久久久| 91偷拍一区二区三区精品| 制服丝袜综合网| 青草成人免费视频| 色丁香久综合在线久综合在线观看| av影视在线看| av不卡在线免费观看| 日本高清视频一区二区| 亚洲国产精品一区| av不卡一区二区| 狠狠干在线视频| 亚洲成人自拍视频| 热久久这里只有精品| 久久99久国产精品黄毛片色诱| 日本少妇高潮喷水视频| 精品成人免费| jizzjizzxxxx| 亚洲1区2区3区4区| 中文字幕一区久| 日韩国产成人无码av毛片| 色狠狠色噜噜噜综合网| 99久久婷婷国产综合精品电影√| 欧美一区2区三区4区公司二百 | 国产精品久久久久影院老司| 影音先锋男人的网站| 91麻豆福利精品推荐| 91九色美女在线视频| 日韩精品久久一区二区三区| 日韩成人在线电影网| 久久蜜桃香蕉精品一区二区三区| 视频一区欧美精品| 精品91久久| av777777| 国产成人中文字幕| 欧美一区二区三区不卡| 五月天亚洲婷婷| 男女激情视频一区| av在线播放一区| 日本欧美在线视频免费观看| 成视频年人免费看黄网站| 91九色视频导航| 亚洲精品在线免费观看视频| 久久欧美中文字幕| 91超碰成人| 国产探花一区| 精品国模一区二区三区| 午夜伦伦电影理论片费看| 91精品国产91久久久久青草| 久久精品视频在线观看| 久久国产精品一区二区| 精品国产18久久久久久洗澡| 成人av视屏| 六月丁香婷婷激情| 视频一区二区视频| 国产99久久精品一区二区 夜夜躁日日躁 | 久久婷婷亚洲| 青春有你2免费观看完整版在线播放高清| 狠狠色伊人亚洲综合网站色| 久久乐国产精品| 久久久爽爽爽美女图片| 专区另类欧美日韩| 美女网站久久| 亚洲日韩成人| 久久国产精品无码网站| 在线黄色的网站| 国产原创精品视频| 污影院在线观看| 91精品论坛| 青青草国产成人a∨下载安卓| 亚洲免费成人av在线| 亚洲自拍电影| 狠狠综合久久av一区二区老牛| 精品人人人人| 久久久亚洲欧洲日产| 国产精品羞羞答答在线观看| 一区免费视频| 国产精品v日韩精品v欧美精品网站 | 91美女视频网站| 色偷偷成人一区二区三区91 | 欧美第一淫aaasss性| 亚洲美女精品成人在线视频| 国产ts一区二区| 国产色一区二区三区| 国产高清视频免费最新在线|