应将计算逻辑从render中移出,用usememo缓存派生数据、usecallback缓存函数、自定义hook解耦复杂逻辑,避免重复计算和隐式重渲染。

因为每次重渲染都会重新执行,哪怕数据根本没变,计算结果也得重算一遍——白耗 CPU,还拖慢界面响应。
计算逻辑会随每次渲染强制重跑
Render 函数本质是“快照生成器”:只要组件状态或 props 变了,框架就调用它生成新 UI。如果里面写了排序、过滤、遍历千条数据、格式化嵌套对象等操作,这些代码就会在每次渲染中无差别执行。
- 比如输入框内容变化,触发 state 更新,即使你只改了个无关的 search 字段,render 里那段 TOP10 平均值计算仍会完整跑一遍
- 再比如父子组件联动时,父组件重渲染,子组件 render 也会跟着执行——里面的计算照样重复
引用不稳定会隐式触发多余渲染
在 render 中直接写函数、对象或数组字面量,会产生新的引用。这些临时值传给子组件或作为 props 时,会导致子组件误判为“数据变了”,从而被动重渲染。
-
❌ 错误示范:
onClick={() => doSomething()}或style={{ color: 'blue' }}—— 每次都新建函数/对象 - ✅ 正确做法:用 useCallback 缓存函数,用 useMemo 缓存对象或计算结果,确保引用稳定
逻辑混在 render 里会让调试和维护变困难
一个 render 函数本该专注“把数据变成结构”,一旦塞进大量 if-else、map、reduce、格式化工具链,它就从视图层滑向业务层,变得臃肿难读。
- 无法单独测试计算逻辑,只能靠整页渲染来验证
- 多人协作时,别人很难一眼分辨哪些是渲染行为,哪些是副作用或派生数据
- 后续加缓存、加防抖、加 loading 状态,都会让 render 更混乱
替代方案:把计算提前、缓存、解耦
把耗时或依赖明确的逻辑从 render 中移出,交给更合适的位置处理:
- 用 useMemo 封装派生数据(如排序列表、聚合统计),依赖项写清楚,变才算、不变就复用
- 用 useCallback 包裹事件处理器,避免因函数引用变化导致子组件不必要更新
- 复杂流程可封装成自定义 Hook(如
useSortedData、useFormattedTitle),实现逻辑复用与关注点分离 - 若计算极度耗时(如大数据量解析),考虑放在 useEffect 或 Web Worker 中异步处理,再把结果同步进状态










