React状态连续更新后,中间状态是否会渲染到DOM?
React状态更新与DOM渲染疑问解答
你的核心疑问是:点击按钮后,中间状态"one"和"two"会不会哪怕极短时间内渲染到DOM上?答案要分React版本来看:
React 17及更早版本
真实DOM确实会短暂更新为"one"和"two",但你肉眼完全看不到。原因是:
- 点击按钮触发事件处理函数,调用
setStatus("one"),React会触发第一次渲染:生成对应"one"的Virtual DOM,对比后更新真实DOM为"one"。 - 渲染完成后执行Effect Hook,第一个Effect检测到
status === "one",调用setStatus("two"),这会立刻触发第二次渲染:更新真实DOM为"two"。 - 接着第二个Effect检测到
status === "two",调用setStatus("three"),触发第三次渲染:更新真实DOM为"three"。 - 这三次DOM更新都在同一个浏览器宏任务里完成,而浏览器只会在宏任务全部执行完毕后才会刷新UI。也就是说,屏幕还没来得及显示"one"或"two",DOM已经变成"three"了。
React 18版本
中间状态"one"和"two"完全不会渲染到真实DOM,因为React 18引入了自动批量更新机制:
- 不管是事件处理函数还是Effect Hook里的状态更新,都会被React合并到一个队列中。
- 点击按钮后,
setStatus("one")、setStatus("two")、setStatus("three")这三次更新会被批量处理,React只会进行一次渲染计算,直接生成对应"three"的Virtual DOM,对比后把真实DOM从"zero"更新为"three"。 - 中间的"one"和"two"对应的Virtual DOM都不会被生成,自然也不会有真实DOM的更新。
结合核心概念的解释
- Virtual DOM:是React对真实DOM的轻量级描述,每次状态变化都会生成新的Virtual DOM树,但批量更新时中间状态的Virtual DOM会被跳过(React 18)。
- DOM Reconciliation(DOM协调):React对比新旧Virtual DOM的差异,只更新需要变化的部分。批量更新下,React会等待所有状态更新完成后再执行一次协调,减少真实DOM的操作次数。
- 组件渲染:指从状态生成Virtual DOM的过程,React 18的批量更新会跳过中间状态的渲染,直接计算最终状态的Virtual DOM。
- Effect Hook:在真实DOM更新完成后执行,它触发的状态更新在React 18中会被自动批量处理,避免了不必要的中间渲染和DOM操作。
内容的提问来源于stack exchange,提问作者Bertuz
相关产品推荐
相关产品推荐

