React 18 之前,只有事件处理函数里的多次 setState 会被合并成一次渲染;18 起所有更新——包括 setTimeout、Promise、原生事件回调中的 setState——都会自动批处理,无论更新发生在哪都合并为一次重渲染。该行为由 createRoot 启用的新调度器提供。

典型收益:网络回调里连续 setLoading(false)、setData(data) 只渲染一次。如需退出批处理(例如更新后立即读取 DOM 布局),可用 flushSync。易错点:批处理只合并同一事件循环 tick 内的更新;class 组件同样受益;React 17 及以前异步回调中不批处理,升级后部分测试快照和时序假设会变化。追问:批处理与 lane 优先级的关系、flushSync 的适用场景与代价。

fetch().then(() => { setData(d); setLoading(false) }) // 只渲染一次