触发状态更新
当你在组件里调用:
this.setState({ count: this.state.count + 1 });
React 并不会马上修改 this.state,而是 把更新请求放到一个队列中(即所谓的异步/批量更新机制)。
合并新旧状态
-
React 会将你传入的对象 { count: newValue } 和现有的 state 合并(shallow merge,浅合并)。
-
如果传入的是函数 setState((prevState, props) => {...}),React 会先执行这个函数,得到新的部分 state,再合并。
标记组件需要更新
-
React 在内部给该组件打上一个 “需要重新渲染” 的标记。
-
但此时不会立即更新 UI,而是交给 调度器(Scheduler) 统一管理,可能会延迟批处理(提高性能)。
调用 Reconciliation(协调算法)
-
React 会触发 虚拟 DOM 的 diff 过程,比较更新前后的 Virtual DOM 树。
-
找出需要真正修改的部分(例如某个
<span>
的文字变了,而不是整个组件都重建)。
渲染更新(Commit 阶段)
-
React 把差异(DOM diff 结果)应用到真实 DOM 上。
-
更新 UI,同时调用相关生命周期方法 / hooks:
-
类组件:componentDidUpdate
-
函数组件:useEffect(在 commit 后执行)
触发副作用
-
例如 useEffect 的回调函数执行。
-
如果有 setState 在这些副作用里,会再次触发更新,进入新的更新循环。
流程总结
调用 setState()↓
将更新加入队列(可能批处理)↓
合并 state↓
标记组件需要更新↓
虚拟 DOM diff↓
最小化更新真实 DOM↓
调用生命周期 / hooks
小知识点
-
setState 是 异步的(React 会合并多次调用以优化性能)。
-
如果你需要拿到更新后的 state,可以用:
this.setState((prev) => ({ count: prev.count + 1 }), () => {console.log(this.state.count); // 回调里能拿到最新值
});
- React 18 以后,在事件回调里,setState 默认是批量的。