在react內(nèi)部其實已經(jīng)使用了許多的技術去使得更新ui時對dom的操作代價最小化猎拨。對許多應用來說,使用react可以在沒有使用特別優(yōu)化手段的情況下獲得更快的用戶界面,即使如此,我們的react仍然有著許多的方式可以使得應用更加流暢酪耳。
使用生產(chǎn)環(huán)境下的構建
如果你在對你的應用進行性能分析或者遇到了性能問題,請確保你在打包構建應用時使用了生產(chǎn)環(huán)境下的配置項刹缝。
開發(fā)環(huán)境即development mode下碗暗,react會提供許多有用的警告,但這些警告功能會使得應用體積增加赞草、反應速度變慢讹堤,所以你應該確保使用生產(chǎn)環(huán)境下的打包編譯配置。
如果你無法確定你的打包過程是否正確厨疙,你可以通過安裝chrome的插件來檢查。https://chrome.google.com/webstore/detail/react-developer-tools/fmkadmapgofadopljbjfkapdkoienihi
create-react-app
如果你使用的是create-react-app來創(chuàng)建并打包編譯項目疑务,當你運行npm run build
時沾凄,就會得到一個生產(chǎn)環(huán)境下的編譯結果,但請記住知允,這僅僅在部署階段才時必要的撒蟀,在開發(fā)時請使用npm start
single-file builds
我們提供了適用于生產(chǎn)環(huán)境的react和react-dom庫文件。
<script src="https://unpkg.com/react@16/umd/react.production.min.js"></script>
<script src="https://unpkg.com/react-dom@16/umd/react-dom.production.min.js"></script>
Brunch
使用webpack插件 uglify-js-brunch 可以將你的js文件最小化
yarn add --dev uglify-js-brunch
brunch build -p
但請注意温鸽,這種做法只建議在生產(chǎn)環(huán)境下使用保屯,因為會去掉react的警告功能,并且這種打包過程會消耗更多的時間涤垫。
展示長列表
如果你的應用會渲染大量的列表數(shù)據(jù)姑尺,我們建議使用一種稱為‘windowing’的技術,這種技術下在任何給定的時間內(nèi)只會渲染一小部分數(shù)據(jù)列表蝠猬,并可以減少列表項的重復渲染(即再次渲染已經(jīng)渲染過的數(shù)據(jù))切蟋。
react-window
和react-virtualized
都是流行的使用windowing技術的庫,他們都提供了一系列可重用的組件榆芦,這些組件能夠幫助你以最好的性能展示列表以及表格數(shù)據(jù)柄粹。你也可以自己實現(xiàn)自己的windowing組件喘鸟,如果你需要某些高度定制化的功能的話。
避免 reconciliation
react在內(nèi)部維護著一個代表其ui結構的對象驻右,它包含了從你的組件中返回的元素什黑,這個對象有效避免了react對真實dom進行不必要的操作,因為操作真實dom所耗費的性能遠遠大于操作js對象堪夭,我們通常將這個js對象稱為‘虛擬dom’愕把,當一個組件的屬性或者性質(zhì)發(fā)生改變的時候,react會根據(jù)新生成的元素與之前虛擬dom的元素是否一致來決定是否重新渲染真實dom茵瘾。
即使react只會更新真正發(fā)生改變的dom礼华,這仍然需要一點時間來完成,當然這在大多數(shù)情況下都是在難以察覺的一瞬間完成的拗秘,但如果這個過程真的造成了可察覺的延遲現(xiàn)象圣絮,就需要使用鉤子函數(shù)shoudComponentUpdate
來重寫其判斷過程,這個鉤子函數(shù)會在更新組件之前執(zhí)行并決定著該組件是否會更新雕旨。
如果你明確知道你的組件在何種情況下需要或是不需要更新扮匠,你可以通過改寫這個鉤子函數(shù)來跳過其內(nèi)部默認的reconciliation過程。
大多數(shù)情況下凡涩,我們會使用繼承PureComponent
而不是改寫鉤子函數(shù)來處理上述問題棒搜,PureComponent
在進行reconciliation時僅僅會對組件的屬性和狀態(tài)進行淺層比較。
使用 immutable.js
當我們使用了PureCOmponen
時活箕,無法追蹤到深層對象屬性的變化力麸,因此會造成某些異常表現(xiàn),但是每次對深層對象進行復制又會產(chǎn)生額外的性能開銷育韩,好在immutablejs致力于解決這一點并卓有成效克蚂,我們可以對immutable對象進行基于內(nèi)容的比較而不是基于指針地址的比較。