React虛擬DOM淺析

如果您正在使用React或?qū)W習(xí)React锌杀,那么您一定聽說過“虛擬DOM”一詞∈チ裕現(xiàn)在什么是虛擬DOM?為什么React使用它隘弊?

真實(shí)DOM
首先哈踱,DOM代表“文檔對(duì)象模型”。DOM用簡(jiǎn)單的語(yǔ)言表示應(yīng)用程序的UI梨熙。每當(dāng)應(yīng)用程序UI的狀態(tài)發(fā)生變化時(shí)开镣,DOM都會(huì)更新以表示該變化。現(xiàn)在咽扇,問題是經(jīng)常操縱DOM影響性能邪财,使其變慢。

是什么導(dǎo)致DOM操作緩慢质欲?
DOM表示為樹數(shù)據(jù)結(jié)構(gòu)树埠。因此,DOM的更改和更新很快嘶伟。但是在更改之后怎憋,必須重新渲染已更新的元素及其子元素以更新應(yīng)用程序UI。UI的重新渲染或重新繪制使它變慢九昧。因此盛霎,您擁有的UI組件越多,DOM更新的成本就越高耽装,因?yàn)槊看蜠OM更新都需要重新渲染它們愤炸。

虛擬DOM

那就是虛擬DOM概念出現(xiàn)的地方,并且其性能要比真實(shí)DOM好得多掉奄。虛擬DOM只是DOM的虛擬表示规个。每當(dāng)我們的應(yīng)用程序狀態(tài)更改時(shí)凤薛,虛擬DOM就會(huì)更新,而不是真實(shí)DOM诞仓。

好吧缤苫,您可能會(huì)問:“虛擬DOM是否與真實(shí)DOM所做的相同,這聽起來(lái)像是雙重工作墅拭?這比僅僅更新真實(shí)的DOM還要快嗎活玲?”

答案是虛擬DOM更快,更高效谍婉,這就是原因舒憾。

虛擬DOM如何更快?

將新元素添加到UI時(shí)穗熬,將創(chuàng)建表示為樹的虛擬DOM镀迂。每個(gè)元素都是該樹上的一個(gè)節(jié)點(diǎn)。如果這些元素中任何一個(gè)的狀態(tài)改變唤蔗,那么將創(chuàng)建一個(gè)新的虛擬DOM樹探遵。然后將該樹與先前的虛擬DOM樹進(jìn)行比較或“差異化”。

完成此操作后妓柜,虛擬DOM將計(jì)算出最佳方法以對(duì)真實(shí)DOM進(jìn)行這些更改箱季。這樣可以確保對(duì)實(shí)際DOM的操作最少。因此棍掐,降低了更新實(shí)際DOM的性能成本规哪。

下圖顯示了虛擬DOM樹和差異化過程。


虛擬DOM

紅色圓圈表示已更改的節(jié)點(diǎn)塌衰。這些節(jié)點(diǎn)表示狀態(tài)已更改的UI元素。然后計(jì)算虛擬DOM樹的先前版本與當(dāng)前虛擬DOM樹之間的差異蝠嘉。然后重新渲染整個(gè)父子樹以提供更新的UI最疆。然后將此更新的樹批量更新為真實(shí)的DOM。

React如何使用虛擬DOM

現(xiàn)在您對(duì)虛擬DOM是什么以及它如何對(duì)您的應(yīng)用程序性能有所了解了蚤告,讓我們了解一下React如何利用虛擬DOM努酸。

在React中,每個(gè)UI塊都是一個(gè)組件杜恰,每個(gè)組件都有一個(gè)狀態(tài)获诈。React遵循可觀察的模式,并監(jiān)聽狀態(tài)變化心褐。當(dāng)組件的狀態(tài)改變時(shí)舔涎,React更新虛擬DOM樹。虛擬DOM更新后逗爹,React然后將虛擬DOM的當(dāng)前版本與虛擬DOM的先前版本進(jìn)行比較亡嫌。此過程稱為“差異化”。

一旦React知道哪些虛擬DOM對(duì)象已更改,然后React就會(huì)在真實(shí)DOM中僅 更新那些對(duì)象挟冠。與直接操作真實(shí)DOM相比于购,這使性能好得多。這使React作為高性能JavaScript庫(kù)脫穎而出知染。

簡(jiǎn)而言之肋僧,您可以告訴React您希望UI處于什么狀態(tài),并確保DOM匹配該狀態(tài)控淡。這里最大的好處是嫌吠,作為開發(fā)人員,您將不需要知道如何在后臺(tái)進(jìn)行屬性操縱逸寓,事件處理或手動(dòng)DOM更新居兆。

所有這些細(xì)節(jié)都是從React開發(fā)人員那里抽象出來(lái)的。您需要做的就是在需要時(shí)更新組件的狀態(tài)竹伸,React負(fù)責(zé)其余的工作泥栖。這樣可以確保在使用React時(shí)獲得卓越的開發(fā)人員體驗(yàn)。

React render()函數(shù)

render()是更新和渲染UI的位置勋篓。render()是React中必需的生命周期方法吧享。render()函數(shù)是創(chuàng)建React元素樹的入口點(diǎn)。當(dāng)組件中的狀態(tài)或道具更新時(shí)譬嚣,render()將返回不同的React元素樹钢颂。如果在組件內(nèi)使用setState() ,React會(huì)立即檢測(cè)到狀態(tài)更改并重新渲染組件拜银。

然后殊鞭,React找出如何有效地更新UI以匹配最新的樹更改。

這是當(dāng)React首先更新其虛擬DOM并僅更新實(shí)際DOM中已更改的對(duì)象時(shí)尼桶。

批量更新

React遵循批處理更新機(jī)制來(lái)更新實(shí)際DOM操灿。因此,導(dǎo)致性能提高泵督。這意味著對(duì)真實(shí)DOM的更新將分批發(fā)送趾盐,而不是針對(duì)狀態(tài)的每個(gè)單個(gè)更改發(fā)送更新。

UI的重新繪制是最昂貴的部分小腊,React有效地確保了真正的DOM僅接收批量更新來(lái)重新繪制UI

總結(jié)

  • 頻繁的DOM操作昂貴且性能沉重救鲤。
  • 虛擬DOM是真實(shí)DOM的虛擬表示。
  • 狀態(tài)發(fā)生變化時(shí)秩冈,將更新虛擬DOM本缠,并比較虛擬DOM的先前版本和當(dāng)前版本。這稱為diff入问。
  • 然后搓茬,虛擬DOM將批量更新發(fā)送到真實(shí)DOM以更新UI犹赖。
  • React使用虛擬DOM來(lái)增強(qiáng)其性能。
  • 它使用可觀察對(duì)象來(lái)檢測(cè)狀態(tài)和道具更改卷仑。
  • React使用高效的差異算法來(lái)比較虛擬DOM的版本峻村。
  • 然后,確保將批處理的更新發(fā)送到真實(shí)的DOM锡凝,以重新繪制或重新呈現(xiàn)UI粘昨。

參考

React Virtual DOM Explained in Simple English

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市窜锯,隨后出現(xiàn)的幾起案子张肾,更是在濱河造成了極大的恐慌,老刑警劉巖锚扎,帶你破解...
    沈念sama閱讀 216,843評(píng)論 6 502
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件吞瞪,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡驾孔,警方通過查閱死者的電腦和手機(jī)芍秆,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,538評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)翠勉,“玉大人妖啥,你說我怎么就攤上這事《月担” “怎么了荆虱?”我有些...
    開封第一講書人閱讀 163,187評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)朽们。 經(jīng)常有香客問我怀读,道長(zhǎng),這世上最難降的妖魔是什么骑脱? 我笑而不...
    開封第一講書人閱讀 58,264評(píng)論 1 292
  • 正文 為了忘掉前任菜枷,我火速辦了婚禮,結(jié)果婚禮上惜姐,老公的妹妹穿的比我還像新娘。我一直安慰自己椿息,他們只是感情好歹袁,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,289評(píng)論 6 390
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著寝优,像睡著了一般条舔。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上乏矾,一...
    開封第一講書人閱讀 51,231評(píng)論 1 299
  • 那天孟抗,我揣著相機(jī)與錄音迁杨,去河邊找鬼。 笑死凄硼,一個(gè)胖子當(dāng)著我的面吹牛铅协,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播摊沉,決...
    沈念sama閱讀 40,116評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼狐史,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了说墨?” 一聲冷哼從身側(cè)響起骏全,我...
    開封第一講書人閱讀 38,945評(píng)論 0 275
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎尼斧,沒想到半個(gè)月后姜贡,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,367評(píng)論 1 313
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡棺棵,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,581評(píng)論 2 333
  • 正文 我和宋清朗相戀三年楼咳,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片律秃。...
    茶點(diǎn)故事閱讀 39,754評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡爬橡,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出棒动,到底是詐尸還是另有隱情糙申,我是刑警寧澤,帶...
    沈念sama閱讀 35,458評(píng)論 5 344
  • 正文 年R本政府宣布船惨,位于F島的核電站柜裸,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏粱锐。R本人自食惡果不足惜疙挺,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,068評(píng)論 3 327
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望怜浅。 院中可真熱鬧铐然,春花似錦、人聲如沸恶座。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,692評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)跨琳。三九已至自点,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間脉让,已是汗流浹背桂敛。 一陣腳步聲響...
    開封第一講書人閱讀 32,842評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工功炮, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人术唬。 一個(gè)月前我還...
    沈念sama閱讀 47,797評(píng)論 2 369
  • 正文 我出身青樓薪伏,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親碴开。 傳聞我的和親對(duì)象是個(gè)殘疾皇子毅该,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,654評(píng)論 2 354

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