白嫖 React 性能优化?是的,用 React.memo!

学习 React 的路上,我总有一种"写着写着就卡顿"的感觉。

后来我才知道,是我把组件喂得太勤快了,明明 props 没变,它还天天重新渲染。

于是我学会了一个"能懒就懒"的技能:React.memo。


前言:

学习 React 的过程中,我发现组件之间的"沟通"和"重渲染"像极了人际关系:

  • 有些组件明明没变,但却天天"参与社交",性能开销像请客吃饭一样频繁。
  • 我开始意识到:我需要一个"宅属性组件",不必要就别出门,别浪费资源!

于是,我遇见了 React.memo ------ 一个能让组件"装死"的优化黑科技。


React.memo 是什么?

一句话解释:

React.memo 是一个高阶组件(HOC),用于缓存函数组件的渲染结果,只有当 props 真正发生变化时才重新渲染。

官方定义(翻译版):

js 复制代码
const MemoizedComponent = React.memo(Component)

当你用 React.memo 包裹一个组件,它就会对传入的 props 进行 浅比较:

  • 如果 props 没变,组件就直接复用上次的渲染结果。
  • 如果 props 变了,才会重新渲染。

说白了,它帮你判断:"这个组件到底有没有必要更新?"


举个例子更香

来看个小例子,假设你有一个 todo 项组件:

js 复制代码
const TodoItem = ({ todo }) => {
  console.log('渲染了:', todo.text);
  return <li>{todo.text}</li>;
};

你把它放在一个列表里:

js 复制代码
function TodoList({ todos }) {
  return (
    <ul>
      {todos.map((todo) => (
        <TodoItem key={todo.id} todo={todo} />
      ))}
    </ul>
  );
}

每当你新增一个 todo,所有 TodoItem 都会重新渲染,哪怕它们根本没变。

🧙‍♂️ 用 React.memo 优化一下:

js 复制代码
const TodoItem = React.memo(({ todo }) => {
  console.log('渲染了:', todo.text);
  return <li>{todo.text}</li>;
});

✨只会渲染新增的那一项,其余的组件都被 memo 缓存住了!


memo 做了什么?到底"懒"在哪?

React.memo 做的就是浅比较(shallow compare) :

js 复制代码
(prevProps, nextProps) => {
  return prevProps === nextProps; // 或每一项都 ===
}

所以你传的 props 要注意:

js 复制代码
<TodoItem todo={{ text: '喝水' }} />

上面这种每次都是新对象(新引用),即使值一样,memo 也认不出来。

正确写法:

js 复制代码
const stableTodo = useMemo(() => ({ text: '喝水' }), []);
<TodoItem todo={stableTodo} />

搭配 useMemo 和 useCallback 才能把 memo 的威力完全释放!


🧯 memo 的误区(踩坑警告⚠️)

情况 是否推荐使用 memo
组件很复杂、渲染成本高 ✅ 推荐
props 基本不变 ✅ 推荐
组件很简单、props 频繁变 ❌ 没必要
每次 props 都是新对象 ❌ memo 白搭

❗不要给所有组件都加 memo!

memo 本身也有性能成本,不变才优化,变了反而浪费对比时间。


自定义对比函数,让 memo 更聪明

js 复制代码
const MyComponent = React.memo((props) => {
  return <div>{props.name}</div>;
}, (prevProps, nextProps) => {
  // 返回 true 表示一样,不更新
  return prevProps.name === nextProps.name;
});

你可以自定义判断逻辑,比如对嵌套对象、函数类型做更复杂的判断。


总结一下:我学到什么了?

知识点 理解方式
React.memo 是干嘛的 缓存组件,防止无用渲染
它做了什么 对 props 做浅比较,props 没变就跳过更新
使用场景 重组件、纯展示组件、性能敏感区域
搭配技巧 useMemo、useCallback
使用风险 props 变化频繁或为新对象时,memo 失效

🧪 面试官问我 React.memo,我怎么答?

React.memo 是一个用于优化函数组件性能的高阶组件,底层通过浅比较 props 判断组件是否需要更新。适合用于渲染成本高、props 稳定的组件,能减少不必要的重复渲染。在大型项目中常搭配 useMemo / useCallback 一起使用,提升性能。

完美收官!


最后一句话:React.memo,是你写"懒惰但高效组件"的第一步

如果你也正在 React 路上摸爬滚打,想进阶、想优化、想提升,记住:

有时候,写出"不做事"的组件,才是高阶开发者的智慧 😎


如果你觉得这篇文章对你有帮助,点个赞 + 收藏支持一下吧!

评论区也欢迎一起交流你踩过的 memo 坑,或者你用 memo 做过的优化!

相关推荐
AiMan几秒前
千问生成的内容能否下载吗?
前端
北城笑笑1 分钟前
Vue 109 ,从零搭建 Vue3 + Electron 工程:生态、安全桥接与打包选型( Vue + Electron )
前端·javascript·vue.js·安全·electron·vue
JarvanMo15 分钟前
Flutter 3.50 & Dart 3.14发布,一起看看有哪些变化!
前端
莪_幻尘29 分钟前
4 个 3D 游戏,总体积 3.82MB:拆解 Claude 的 one-shot 工程链路
前端·ai编程·three.js
Highcharts.js37 分钟前
Highcharts智能数据分析平台Orbit 多语言配置技术文档
java·前端·javascript·highcharts·orbit·智能数据分析·设置文档
ABAP-張旺1 小时前
SAP ABAP 实战:SAP GUI上做 HTML 看板报表
前端·html·sap·abap
时间的情敌2 小时前
Cesium 建筑单体化、3DTiles 分类、楼层显隐、分户高亮(BIM + 倾斜孪生高频)
前端·3d·cesium
IT_陈寒2 小时前
JavaScript项目实战经验分享:从内存泄漏到性能优化的血泪史
前端·人工智能·后端
恋猫de小郭3 小时前
Flutter 3.50 & Dart 3.14 发布,快来看看有什么更新吧
android·前端·flutter
非优秀程序员11 小时前
第10章 千团出世|《互联网产品恩仇录》
前端