9.6-全棧Java筆記:二叉樹和紅黑二叉樹

二叉樹的定義

二叉樹是樹形結(jié)構(gòu)的一個(gè)重要類型。 許多實(shí)際問題抽象出來的數(shù)據(jù)結(jié)構(gòu)往往是二叉樹的形式垄提,即使是一般的樹也能簡(jiǎn)單地轉(zhuǎn)換為二叉樹,而且二叉樹的存儲(chǔ)結(jié)構(gòu)及其算法都較為簡(jiǎn)單,因此二叉樹顯得特別重要器虾。

二叉樹(BinaryTree)由一個(gè)結(jié)點(diǎn)及兩棵互不相交的躬窜、分別稱作這個(gè)根的左子樹和右子樹的二叉樹組成浇垦。下圖中展現(xiàn)了五種不同基本形態(tài)的二叉樹。

(a)?為空樹

(b)?為僅有一個(gè)結(jié)點(diǎn)的二叉樹

(c)?是僅有左子樹而右子樹為空的二叉樹

(d)?是僅有右子樹而左子樹為空的二叉樹

(e)?是左荣挨、右子樹均非空的二叉樹男韧。

?

這里應(yīng)特別注意的是,二叉樹的左子樹和右子樹是嚴(yán)格區(qū)分并且不能隨意顛倒的默垄,圖?(c)?與圖?(d)?就是兩棵不同的二叉樹此虑。

排序二叉樹

排序二叉樹特性如下:

1. 左子樹上所有節(jié)點(diǎn)的值均小于它的根節(jié)點(diǎn)的值

2. 右子樹上所有節(jié)點(diǎn)的值均大于它的根節(jié)點(diǎn)的值

比如:我們要將數(shù)據(jù)【14,12,23,4,16,13, 8,,3】存儲(chǔ)到排序二叉樹中:

排序二叉樹本身實(shí)現(xiàn)了排序功能,可以快速檢索口锭。但如果插入的節(jié)點(diǎn)集本身就是有序的朦前,要么是由小到大排列,要么是由大到小排列鹃操,那么最后得到的排序二叉樹將變成普通的鏈表韭寸,其檢索效率就會(huì)很差。 比如上面的數(shù)據(jù)【14,12,23,4,16,13, 8,,3】荆隘,我們先進(jìn)行排序變成:【3,4,8,12,13,14,16,23】恩伺,然后存儲(chǔ)到排序二叉樹中,顯然就變成了鏈表椰拒。

平衡二叉樹(AVL)

為了避免出現(xiàn)一邊倒的存儲(chǔ)晶渠,科學(xué)家提出了“平衡二叉樹”。

在平衡二叉樹中任何節(jié)點(diǎn)的兩個(gè)子樹的高度最大差別為1燃观,所以它也被稱為高度平衡樹褒脯。 增加和刪除節(jié)點(diǎn)可能需要通過一次或多次樹旋轉(zhuǎn)來重新平衡這個(gè)樹。


節(jié)點(diǎn)的平衡因子是它的左子樹的高度減去它的右子樹的高度(有時(shí)相反)仪壮。帶有平衡因子1憨颠、0或 -1的節(jié)點(diǎn)被認(rèn)為是平衡的。帶有平衡因子 -2或2的節(jié)點(diǎn)被認(rèn)為是不平衡的,并需要重新平衡這個(gè)樹爽彤。

比如养盗,我們存儲(chǔ)排好序的數(shù)據(jù)【3,4,8,12,13,14,16,23】,增加節(jié)點(diǎn)如果出現(xiàn)不平衡适篙,則通過節(jié)點(diǎn)的左旋或右旋往核,重新平衡樹結(jié)構(gòu),最終平衡二叉樹如下:

平衡二叉樹追求絕對(duì)平衡嚷节,實(shí)現(xiàn)起來比較麻煩聂儒,每次插入新節(jié)點(diǎn)需要做的旋轉(zhuǎn)操作次數(shù)不能預(yù)知。

紅黑二叉樹

紅黑二叉樹(簡(jiǎn)稱:紅黑樹)硫痰,它首先是一顆二叉樹衩婚,同時(shí)也是一顆自平衡的排序二叉樹。

紅黑樹在原有的排序二叉樹增加了如下幾個(gè)要求:

性質(zhì)?1:每個(gè)節(jié)點(diǎn)要么是紅色效斑,要么是黑色非春。

性質(zhì)?2:根節(jié)點(diǎn)永遠(yuǎn)是黑色的。

性質(zhì)?3:所有的葉節(jié)點(diǎn)都是空節(jié)點(diǎn)(即?null)缓屠,并且是黑色的奇昙。

性質(zhì)?4:每個(gè)紅色節(jié)點(diǎn)的兩個(gè)子節(jié)點(diǎn)都是黑色。(從每個(gè)葉子到根的路徑上不會(huì)有兩個(gè)連續(xù)的紅色節(jié)點(diǎn))

性質(zhì)?5:從任一節(jié)點(diǎn)到其子樹中每個(gè)葉子節(jié)點(diǎn)的路徑都包含相同數(shù)量的黑色節(jié)點(diǎn)敌完。


這些約束強(qiáng)制了紅黑樹的關(guān)鍵性質(zhì):從根到葉子的最長(zhǎng)的可能路徑不多于最短的可能路徑的兩倍長(zhǎng)储耐。這樣就讓樹大致上是平衡的。

紅黑樹是一個(gè)更高效的檢索二叉樹滨溉,JDK?提供的集合類?TreeMap什湘、TreeSet?本身就是一個(gè)紅黑樹的實(shí)現(xiàn)。

【圖】一個(gè)典型的紅黑樹(考慮書本印刷問題业踏,淺色表示紅色禽炬,深色表示紅色)

紅黑樹的基本操作:插入、刪除勤家、左旋腹尖、右旋、著色伐脖。?每插入或者刪除一個(gè)節(jié)點(diǎn)热幔,可能會(huì)導(dǎo)致樹不在符合紅黑樹的特征,需要進(jìn)行修復(fù)讼庇,進(jìn)行?“左旋绎巨、右旋、著色”操作蠕啄,使樹繼續(xù)保持紅黑樹的特性场勤。

老鳥建議

本節(jié)關(guān)于二叉樹的介紹戈锻,僅限于了解。實(shí)際開發(fā)中和媳,直接用到的概率非常低格遭。普通企業(yè)面試中也較少。不過留瞳,極有可能出現(xiàn)在BAT等企業(yè)筆試中拒迅。建議,想進(jìn)BAT等名企的童鞋她倘,專門準(zhǔn)備一下數(shù)據(jù)結(jié)構(gòu)相關(guān)的知識(shí)璧微。

TreeMap的使用和底層實(shí)現(xiàn)

TreeMap是紅黑二叉樹的典型實(shí)現(xiàn)。我們打開TreeMap的源碼硬梁,發(fā)現(xiàn)里面有一行核心代碼:

private?transient?Entry<K,V>?root?=?null;

?root用來存儲(chǔ)整個(gè)樹的根節(jié)點(diǎn)前硫。我們繼續(xù)跟蹤Entry(是TreeMap的內(nèi)部類)的代碼:

static?final?class?? Entry<K,V>?implements?? Map.Entry<K,V> {

??? K?key;

??????? V?value;

??????? Entry<K,V>?left?=?null;

??????? Entry<K,V>?right?=?null;

??????? Entry<K,V>?parent;

????????boolean?color?= ? BLACK;

}

可以看到里面存儲(chǔ)了本身數(shù)據(jù)、左節(jié)點(diǎn)靶溜、右節(jié)點(diǎn)开瞭、父節(jié)點(diǎn)懒震、以及節(jié)點(diǎn)顏色罩息。?TreeMap的put()/remove()方法大量使用了紅黑樹的理論。本書限于篇幅个扰,不再展開瓷炮。需要了解更深入的,可以參考專門的數(shù)據(jù)結(jié)構(gòu)書籍递宅。

TreeMap和HashMap實(shí)現(xiàn)了同樣的接口Map娘香,因此,用法對(duì)于調(diào)用者來說沒有區(qū)別办龄。HashMap效率高于TreeMap烘绽;在需要排序的Map時(shí)才選用TreeMap。




「全棧Java筆記」是一部能幫大家從零到一成長(zhǎng)為全棧Java工程師系列筆記俐填。筆者江湖人稱 Mr. G安接,10年Java研發(fā)經(jīng)驗(yàn),曾在神州數(shù)碼英融、航天院某所研發(fā)中心從事軟件設(shè)計(jì)及研發(fā)工作盏檐,從小白逐漸做到工程師、高級(jí)工程師驶悟、架構(gòu)師胡野。精通Java平臺(tái)軟件開發(fā),精通JAVAEE痕鳍,熟悉各種流行開發(fā)框架硫豆。


? 筆記包含從淺入深的六大部分:

? A-Java入門階段

? B-數(shù)據(jù)庫(kù)從入門到精通

? C-手刃移動(dòng)前端和Web前端

? D-J2EE從了解到實(shí)戰(zhàn)

? E-Java高級(jí)框架精解

? F-Linux和Hadoop?

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子熊响,更是在濱河造成了極大的恐慌恭应,老刑警劉巖,帶你破解...
    沈念sama閱讀 211,561評(píng)論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件耘眨,死亡現(xiàn)場(chǎng)離奇詭異昼榛,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)剔难,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,218評(píng)論 3 385
  • 文/潘曉璐 我一進(jìn)店門胆屿,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人偶宫,你說我怎么就攤上這事非迹。” “怎么了纯趋?”我有些...
    開封第一講書人閱讀 157,162評(píng)論 0 348
  • 文/不壞的土叔 我叫張陵憎兽,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我吵冒,道長(zhǎng)纯命,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 56,470評(píng)論 1 283
  • 正文 為了忘掉前任痹栖,我火速辦了婚禮亿汞,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘揪阿。我一直安慰自己疗我,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,550評(píng)論 6 385
  • 文/花漫 我一把揭開白布南捂。 她就那樣靜靜地躺著吴裤,像睡著了一般。 火紅的嫁衣襯著肌膚如雪溺健。 梳的紋絲不亂的頭發(fā)上麦牺,一...
    開封第一講書人閱讀 49,806評(píng)論 1 290
  • 那天,我揣著相機(jī)與錄音矿瘦,去河邊找鬼枕面。 笑死,一個(gè)胖子當(dāng)著我的面吹牛缚去,可吹牛的內(nèi)容都是我干的潮秘。 我是一名探鬼主播,決...
    沈念sama閱讀 38,951評(píng)論 3 407
  • 文/蒼蘭香墨 我猛地睜開眼易结,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼枕荞!你這毒婦竟也來了柜候?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,712評(píng)論 0 266
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤躏精,失蹤者是張志新(化名)和其女友劉穎渣刷,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體矗烛,經(jīng)...
    沈念sama閱讀 44,166評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡辅柴,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,510評(píng)論 2 327
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了瞭吃。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片碌嘀。...
    茶點(diǎn)故事閱讀 38,643評(píng)論 1 340
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖歪架,靈堂內(nèi)的尸體忽然破棺而出股冗,到底是詐尸還是另有隱情,我是刑警寧澤和蚪,帶...
    沈念sama閱讀 34,306評(píng)論 4 330
  • 正文 年R本政府宣布止状,位于F島的核電站,受9級(jí)特大地震影響攒霹,放射性物質(zhì)發(fā)生泄漏怯疤。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,930評(píng)論 3 313
  • 文/蒙蒙 一剔蹋、第九天 我趴在偏房一處隱蔽的房頂上張望旅薄。 院中可真熱鬧,春花似錦泣崩、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,745評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至第焰,卻和暖如春买优,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背挺举。 一陣腳步聲響...
    開封第一講書人閱讀 31,983評(píng)論 1 266
  • 我被黑心中介騙來泰國(guó)打工杀赢, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人湘纵。 一個(gè)月前我還...
    沈念sama閱讀 46,351評(píng)論 2 360
  • 正文 我出身青樓脂崔,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親梧喷。 傳聞我的和親對(duì)象是個(gè)殘疾皇子砌左,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,509評(píng)論 2 348

推薦閱讀更多精彩內(nèi)容

  • 樹的概述 樹是一種非常常用的數(shù)據(jù)結(jié)構(gòu)脖咐,樹與前面介紹的線性表,棧汇歹,隊(duì)列等線性結(jié)構(gòu)不同屁擅,樹是一種非線性結(jié)構(gòu) 1.樹的定...
    Jack921閱讀 4,442評(píng)論 1 31
  • 4 TreeMap 上一篇,介紹了集合框架中的HashMap對(duì)象产弹,主要講述了HashMap的底層實(shí)現(xiàn)和基本操作派歌。本...
    賈博巖閱讀 120,930評(píng)論 15 98
  • 基于樹實(shí)現(xiàn)的數(shù)據(jù)結(jié)構(gòu),具有兩個(gè)核心特征: 邏輯結(jié)構(gòu):數(shù)據(jù)元素之間具有層次關(guān)系痰哨; 數(shù)據(jù)運(yùn)算:操作方法具有Log級(jí)的平...
    yhthu閱讀 4,256評(píng)論 1 5
  • 前言 今天來介紹下TreeMap,TreeMap是基于紅黑樹結(jié)構(gòu)實(shí)現(xiàn)的一種Map硝皂,要分析TreeMap的實(shí)現(xiàn)首先就...
    嘟爺MD閱讀 5,074評(píng)論 5 37
  • 喂;铩!折欠! 該好好學(xué)了1椿颉!锐秦! 話就放這里了咪奖!不要再玩了!不要再碰其他東西啦 不是讀書沒有用酱床,是你讀書沒用羊赵,關(guān)鍵是 你...
    ooAAMM閱讀 202評(píng)論 0 0