React子节点变更后父组件接收新状态却未重渲染的原因
React父组件收到新state却不重渲染的常见原因
兄弟,我之前也踩过一模一样的坑!你说父组件明明拿到新state却没触发重渲染,大概率是更新state的方式不对,没让React检测到state的引用变化,给你拆解几个最常见的问题:
直接修改原state的对象/数组,没返回新引用
React判断state是否变化用的是浅比较,如果你是这么写的:// 错误示例:直接修改原state里的数组元素 const newRows = this.state.rows; newRows[0].value = "修改后的值"; this.setState({ rows: newRows });这里
newRows还是原数组的引用,React浅比较后会认为rows根本没变化,自然不会触发重渲染。正确的做法是创建新的数组/对象:// 正确示例:解构生成新数组和新对象 const newRows = [...this.state.rows]; newRows[0] = { ...newRows[0], value: "修改后的值" }; this.setState({ rows: newRows });用
setState的函数式写法会更优雅,还能避免异步更新的问题:this.setState(prevState => ({ rows: prevState.rows.map((row, index) => index === 0 ? { ...row, value: "修改后的值" } : row ) }));setState返回的state和原state浅比较相等
如果你的更新逻辑只是把原state直接返回,比如:this.setState(prevState => ({ rows: prevState.rows // 直接返回原数组引用 }));React会判定state没有变化,直接跳过重渲染流程。
类组件误写了shouldComponentUpdate方法
要是你的父组件是类组件,并且重写了shouldComponentUpdate,不小心返回了false,那就算state真的变了,组件也不会重渲染。这种情况可以先注释掉这个方法测试一下。
另外你可以在父组件的render方法里加个console.log('父组件渲染了'),确认是不是真的没渲染——有时候可能是子组件没更新,容易误以为是父组件的问题。如果是子组件的问题,那就要检查子组件是不是用了PureComponent或者React.memo,并且传递的props有没有保持引用稳定。
内容的提问来源于stack exchange,提问作者dudu
相关产品推荐
相关产品推荐

