樹基礎 心得

1.前言

      除了傳統的那些數據結構,例如,線性表,棧,隊列,串,數組,鏈表這些數據結構,但是還有一些情況下,比如說查找,插入,另外一種數據結構會更有優勢那就是樹,這是一種最複雜的數據結構

2 普通的樹

      一般用三種表示方式(存儲方式),分別是雙親表示法,孩子表示法,孩子兄弟表示法

        第一種,雙親表示法可用數組或者鏈表(其實鏈表肯定行的啦)表示,數組中每一個元素有倆個參數分別是本身的數據值,和雙親的位置

        第二種,孩子表示法,首先把元素放進數組中,數組每一項依舊是兩個參數,如果有孩子,那麼節點中的那個位置值(或者說指針)存放第一個孩子的位置,若還有第二                                個孩子,第一個孩子的位置值指向第二個孩子,直到沒有爲止,數組的下一項(第二個節點)也是,這是一個指向的孩子鏈

        第三種,孩子兄弟表示法,也就是一個節點有三個參數,一個是數據值個兩個指針,指向第一個孩子和右兄弟,這樣一來,就成了二叉樹


3 二叉樹

        二叉樹是指有少於或者等於兩個子樹的樹,每一個節點的下方不是一定都是兩棵子樹,有一顆或者一些節點沒有子樹也是可以的

樹中的一個完美的特例是滿二叉樹,也就是每一行都滿了,假如有n層,那麼有2的n次-1個節點,2的n-1次方個葉子


        我們經常說的完全二叉樹就是按照滿二叉樹的順序填滿或者沒填滿,編號從第一層開始從上到下,每一層從左到右編號,
第一層1二層23三層4567~~~ 完全二叉樹由於其結構的特殊性,可以用數組(順序存儲)鏈表都可以表示,
不過普通的二叉樹就不太適合,還是鏈表好,直接用指針指向下一個節點,清晰明瞭,  一般,節點的內容是,一個data和兩個指針,分別指向兩棵子樹

        我們常說二叉樹的前序遍歷,中序遍歷,後序遍歷,還有一種叫層序遍歷,(一層一層的遍歷),爲什麼要有這麼多種遍歷方法呢,是因爲在編程的時候,程序要去訪問二叉樹,電腦只會循環,判斷,因此研究出這些遍歷方法,是爲了幫助電腦遍歷二叉樹的


        簡單說其中一種,中序遍歷,這個中是訪問根節點的順序,中序遍歷,那就是先訪問左子樹,再訪問根節點,最後訪問右子樹,如果左孩子還有孩子節點,那麼先訪問左孩子節點,若還有下一層,那麼就是遞歸了,左中右的順序,(各種遍歷的真正的意義:二叉排序樹,左孩子比父親小,有孩子比父親大,如果使用中序遍歷,那麼出來的訪問順序就是,從小到大的順序

        二叉樹的建立和遍歷都是用遞歸的方式來做的,在建立一棵二叉樹的時候,每個節點有三個成員,分別是數據,data,左右子樹的指針,可以看出,每個葉子的這兩個指針都荒廢了,還有一些節點浪費了其中一個指針,對於追求效率的編程理念來說,這是不允許的,因此要把他利用起來

       這個時候,線索二叉樹應運而生!!!我們知道,二叉樹在其中一個節點要找到左右子樹非常簡單,但是如果像傳統的雙向鏈表那樣找到前驅和後繼,不容易,必須要再遍歷一次,這樣就不方便了,正好把葉子的浪費的這些空間給利用上,一舉兩得!!


       好的,那麼就那中序遍歷來說,如果指向右子樹的指針爲空,那麼就把它指向後繼,因爲本來右子樹就是他的後繼(下一個要訪問的位置),把指向左子樹的空指針指向他的前驅,這樣的話,所有節點的前驅後繼都可以馬上找到了,(邊界除外),這樣的話由於兩個指針都有值了,其實線索二叉樹就變成了雙向鏈表!!!!!!
不過,還有一個問題,那就是所有節點的兩個指針都有值了,那麼就不知道他指向的是子樹還是後繼,這個時候,只要給節點增加兩個標誌位即可,ltag rtag,0表示子樹,1表示後繼

       由於二叉樹的表示比普通的樹要簡單的多,因此人們想出了用二叉樹表示普通樹的想法,把普通樹轉化爲二叉樹,其步驟爲:右兄弟變右孩子,如果一個節點有兩個以上的孩子那麼把這些孩子連起來,除了第一個孩子,其他孩子和雙親的連線斷開,這樣原來的非第一個孩子就變成了第一個孩子(左孩子)的右孩子,這樣就把普通樹轉化成了二叉樹,相反,二叉樹還原爲普通數,把右孩子變成右兄弟
接下來說說把森林轉成二叉樹,其實也不難,首先把森林中的每一棵樹轉成二叉樹,再把第二棵樹開始以後的那些樹,把根節點看成第一棵樹根節點的右兄弟,這樣把右兄弟變右孩子,成功!!!!!若要把二叉樹轉回森林,那麼根節點必須要有右孩子,從根節點開始,根節點的右孩子如果還有右孩子,那就可可分解成三棵樹,以此類推

      森林的遍歷也不難,也就是遍歷裏邊的每一棵樹,比如說先序遍歷一個森林,就是先序遍歷第一課樹,再先序遍歷第二棵樹以此類推


      下面說說一些實際應用中常用到的樹(好吧應聘的時候可能會考到的)

         第一種,二叉排序樹,也稱二叉查找樹首先是樹中的節點是有序的,一般的做法是,根結點A的大小比左孩子B大,比右孩子C小,左孩子B的大小又比其左孩子(B的左孩子)大,比其右孩子小,這樣構造二叉樹的話,查找的時候就很方便了,最多查找的次數就是數的高度,比普通的窮盡查找要高的多,那麼很自然就想到如果每個根結點只有一個孩子,每個孩子也就只有一個孩子,那麼就跟但鏈表差不多了,這個時候最壞的情況是N個節點要查找N次,爲了解決這個問題,我們很自然想到,那就規定每個節點都要有兩個孩子,而且他們的各個子樹的高度有差不多,這就是所謂的平衡二叉樹

        第二種:平衡二叉樹,在查找二叉樹(或者二叉排序樹)的基礎上,每個點的左子樹和右子樹的差別小於1,我們說這棵樹處於平衡狀態,在每次插入新節點的時候後,如果差別超過1,那麼就要調整,直到平衡爲止,調整的方法再另一篇博文中http://blog.csdn.net/dalleny/article/details/38680653  這個時候,很多人都會覺得,平衡條件是子樹高度差小於等於1,那麼新插入節點時,很容易出現不平衡的的情況,調整太頻繁,這個時候,爲了解決這個問題,人們又提出了一種新的樹~~~~紅黑樹


        第三種:紅黑樹  紅黑樹是一種特殊的二叉樹,

紅黑樹有5條規則:1,節點不是紅色就是黑色,2根節點爲黑色,3紅色節點的孩子節點必須爲黑色,4,插入的節點必須爲紅色,5從根節點到任意一個葉子節點的黑結點的個數是一樣的

這5條規則確保了紅黑樹子樹之間的高度差不會出現一個是另一個的兩倍,這樣既可以降低調整的次數(每次插入最多三次),又可以實現比較不錯的平衡,局部平衡,有一個說法:紅黑樹出現了以後,平衡樹就被扔進了博物館


       用於壓縮算法的一種樹~~~~哈夫曼樹,也稱最優二叉樹,使用哈夫曼編碼,可以縮短普通的編碼長度,因而達到壓縮的目的


發佈了19 篇原創文章 · 獲贊 40 · 訪問量 7萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章