setState
不仅仅
只是修改了 this.state 的值,
最重要的是它会触发 React 的更新机制,
会进行 diff ,
然后将 patch 部分更新到真实 dom 里。
如果你直接 this.state.xx == oo 的话,
state 的值确实会改,
但是改了不会触发 UI 的更新,
那就不是数据驱动了。
因为 Vue 在创建 UI 的时候会把这些 data 给收集起来,
并且在这些 data 的访问器属性 setter 进行了重写,
在这个重写的方法里会去触发 UI 的更新。
========================
只在合成事件和钩子函数中是“异步”的,
在原生事件和 setTimeout/setInterval等原生 API 中都是同步的。
被 React 控制的函数里面
就会表现出“异步”,
============================
为了做性能优化,
将 state 的更新延缓到最后批量合并再去渲染对于应用的性能优化是有极大好处的,
如果每次的状态改变都去重新渲染真实 dom,那么它将带来巨大的性能消耗。
====================================
如何在表现出异步的函数里可以准确拿到更新后的 state 呢?
通过第二个参数 setState(partialState, callback) 中的 callback 拿到更新后的结果。
或者可以通过给 setState 传递函数来表现出同步的情况:
this.setState((state) => {
return { val: newVal }
})
=============================
在 React 的 setState 函数实现中,
会根据 isBatchingUpdates(默认是 false) 变量判断
是否直接更新 this.state
还是放到队列中稍后更新。
然后有一个 batchedUpdate 函数,
可以修改 isBatchingUpdates 为 true
,当 React 调用事件处理函数之前,
或者生命周期函数之前就会调用 batchedUpdate 函数,
这样你就可以理解为什么原生事件和 setTimeout/setinterval 里面调用 this.state 会同步更新了吧,
那么这个时候 setState 的时候默认就是 false,那么就会同步更新。
网友评论