React状态值未变化时仍执行组件?附纯组件疑问
关于React严格模式与组件渲染的疑问
背景理解
- React严格模式下会挂载并重新挂载组件,组件会渲染两次
- 当
setState尝试设置与当前相同的原始值时,React不会触发组件重渲染
基于上述理解,对以下代码的执行逻辑有推测:
- 首次渲染:严格模式下组件挂载又重新挂载,
console.log("Hello")打印两次,但ref.current最终为1(因为第一个组件实例被销毁,新实例重新初始化ref) - 首次点击按钮:组件渲染两次,
ref.current增加2变为3,console.log("Hello")打印两次 - 再次点击按钮:因设置相同值不会触发重渲染,
ref.current保持3,但疑惑"Hello"是否仍会打印两次
import React from "react"; import "./style.css"; import {useRef, useState} from 'react'; export default function App(){ const [flag, setFlag]=useState(false); const ref = useRef(0); ref.current+=1; console.log("Hello") return( <> <button onClick={()=>setFlag(true)}>Click</button> <p>Number of renders : {ref.current}</p> </> ) }
疑问
- React是否会在检查新值与当前值是否相同时再次执行组件,导致
"Hello"打印两次? - 该组件是否为纯组件?因为在props和state(值为true)相同的情况下,JSX输出一致。
问题解答
关于重复打印"Hello"的问题
React在严格模式下,为了帮开发者检测副作用,会刻意重复执行组件的渲染逻辑两次——哪怕后续会因为state未变化而跳过实际的DOM更新。所以当你第二次点击按钮调用setFlag(true)时,虽然React会检查到新state和当前state一致,最终不会触发重渲染,但检查前它已经把组件函数执行了两次,自然会打印两次"Hello"。关于是否为纯组件的问题
这个组件不是纯组件。纯组件的要求是:相同的props和state输入,必须返回完全相同的输出,且执行过程中不能产生副作用。但你的组件里直接修改了ref.current,这属于组件渲染期间的副作用;而且每次执行组件函数时,ref.current都会变化,导致JSX里的{ref.current}输出不同——哪怕props和state完全没变,所以不符合纯组件的定义。
内容的提问来源于stack exchange,提问作者Indra
相关产品推荐
相关产品推荐

