为何该场景下修改useRef.current值未触发子组件EmployeeInfo重渲染
问题根因
React 中修改 useRef 的 current 属性不会触发组件重新渲染。
另外 useEffect 执行时机在组件渲染完成之后,当 hobbies 从 undefined 更新为 ["Reading"] 时,组件会先触发一次渲染,此时 hobbyRef.current 还是上一次的空值,渲染完成后才执行 useEffect 正确修改了 ref 的值,但修改 ref 不会触发二次渲染,所以传递给 EmployeeInfo 的属性还是旧值,页面自然看不到新的爱好内容。
修复方案
方案1:移除冗余的 useRef 实现(推荐)
你完全不需要用 useRef 存储当前展示的爱好,直接通过 hobbies 和 indx 计算出要传递的值即可,state 变化会自动触发重渲染,同时还修复了原代码的定时器内存泄漏、索引越界问题:
export const EmployeeInfoWrapper = (props) => { const { hobbies, otherInfo } = props; const [indx, setIndx] = React.useState<number>(0); // 直接计算当前要展示的爱好 const currentHobby = hobbies?.length ? hobbies[indx % hobbies.length] : ""; // 处理轮播逻辑 useEffect(() => { let timer = null; // 仅当爱好数量大于1时启动轮播 if (hobbies?.length > 1) { timer = setTimeout(() => { setIndx(prev => (prev + 1) % hobbies.length); }, 2000); } // 组件卸载/依赖变化时清除定时器,避免内存泄漏 return () => clearTimeout(timer); }, [hobbies, indx]); // 爱好列表变化时重置轮播下标,避免索引越界 useEffect(() => { setIndx(0); }, [hobbies]); return ( <EmployeeInfo hobby={currentHobby} otherInfo={otherInfo} /> ); };
方案2:强制触发重渲染(不推荐)
如果一定要保留 useRef 的实现,可以新增一个无意义的状态变量,修改ref之后更新这个状态强制重渲染,但这种写法冗余且不符合React设计理念,不建议使用。
其他注意事项
你提供的Container组件中传递props的写法存在语法错误,hobbies=hobbies 应该改为 hobbies={hobbies},otherInfo 属性同理。
内容的提问来源于stack exchange,提问作者user6118986
相关产品推荐
相关产品推荐

