为何React在对象引用相同时仍重渲染组件?代码场景疑问
为什么每次点击按钮组件都会重渲染?
你的疑惑核心是误解了obj2的引用逻辑,拆解原因如下:
obj2的引用并非固定不变:因为obj2定义在组件函数内部,每次组件重渲染时,这段变量声明代码都会重新执行——也就是说每次渲染都会创建一个全新的obj2对象,引用地址完全不同。- 第一次点击时,你把新的
obj2引用传给setObj,和原状态obj1的引用不同,触发重渲染符合预期。 - 第二次及后续点击时,组件已经完成过一次重渲染,此时的
obj2是本次渲染新创建的对象,和当前状态里保存的上一个obj2引用完全不一样。所以调用setObj(obj2)时,新状态引用和旧状态引用不相等,React会触发重渲染。
额外补充:
如果把obj2移到组件外面变成全局变量,每次点击的都是同一个引用,这时候调用setObj(obj2),React默认还是会触发重渲染——因为React的setState默认不会做浅比较判断是否需要更新,只要调用了setState,不管新值和旧值是否相等,都会触发重渲染。除非你用React.memo包裹组件,让它通过浅比较props和状态来决定是否重渲染。
另外要注意:直接修改obj2的属性再传给setObj是不规范的写法,属于直接修改状态之外的对象,可能导致不可预测的bug。正确的做法是创建新对象,比如setObj({...obj2, name: User_${2+Math.random()}}),既保证新引用,也符合React的不可变状态原则。
内容的提问来源于stack exchange,提问作者Elchin Babayev
相关产品推荐
相关产品推荐

