異步更新
原因
1設置為異步提升性能 如果setState每次調用直接執行,會造成 render 函數被頻繁執行 ,頁面重新被渲染 解決:異步批處理
2如果render函數未執行時,保證props和state一致性
拿到最新state的方法
法一:setState()中第二個數據是一個回調函數,通過這個回調函數拿到最新的數據
法二:componentDidUpdate()獲取到最新的數據
先執行聲明周期函數在執行回調函數的
在版本17之前有同步更新
情況一:在setTimeout()中
情況二:在原生dom事件中
進行合并
輸出的值為1 僅進行一次加1操作
如何避免:使用函數式更新
原因:在setState源碼中進行判斷,是函數的話會進行call方法的調用,不是進行合并
React的更新機制
JSX => 虛擬dom =>真實dom
更新 state或者props改變 => render函數重新執行 => 比較新舊虛擬dom樹的差別 =>做出更新
diff算法 將比較兩顆樹的時間復雜度優化到了O(n)的數量級
1.同級比較,不夸層 2。類型不同直接刪除 3.引入key值‘
’
key值 尾插時性能優化不大,在中間插入時引入key值用來匹配確定唯一元素
嵌套組件的render被調用 父組件渲染引起子組件更新
解決方法 更新階段函數 shouldComponentUpdate
// 阻斷更新函數shouldComponentUpdate(nextProps,nextState){if(this.state.counter!=nextState.counter){return true}return false}
每個類里都需要 手寫shouldComponentUpdate()函數
解決方法 類組件繼承PureComponent 會自動進行淺比較生成shouldComponentUpdate
原理:更新時shouldCompenontUpdate決定組件是否在render時更新
源碼里面判斷是否用戶自己定義了compenontUpdate函數
而在pureComponent中如果繼承自這個,沒有走上面的流程而是進行一次淺比較
進行state和props的淺層比較 如果沒有的話就不更新 return false