You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

ReactNode作为组件Props时,memo与useMemo的差异及问题解析

React中memo与useMemo的区别及memo失效原因解析

核心问题

用memo包裹Icon组件后作为props传给MenuButton,MenuButton仍会重渲染;但用useMemo缓存Icon组件实例后,重渲染问题消失。这背后的核心是memo和useMemo的作用对象完全不同,以及React元素的引用变化逻辑。

代码问题分析

看你代码里的两个Icon实例:

const icon = useMemo(() => {
  return <BoldIcon />;
}, []);

const memoIcon = <MemoBoldIcon />;
  • 对于memoIcon:每次BoldButton重渲染时,<MemoBoldIcon />都会被重新创建为新的React元素对象(本质是包含组件类型、props等信息的普通对象)。即便MemoBoldIcon本身被memo包裹,它作为props传给MemoMenuButton时,引用已经发生变化。而MemoMenuButton是被memo包裹的组件,会对props做浅比较——发现icon prop的引用更新,就会触发自身重渲染。
  • 对于icon:useMemo会缓存回调返回的<BoldIcon />实例,只要依赖数组(这里是空数组)不变,每次BoldButton重渲染时,icon都是同一个引用。传给MemoMenuButton的icon prop没有变化,因此MemoMenuButton不会重渲染。

memo与useMemo的本质区别

  • memo:是高阶组件,作用于整个组件。功能是当组件props经浅比较无变化时,跳过该组件的重渲染,但无法控制父组件传递props时是否创建新引用。
  • useMemo:是React Hook,作用于单个值/对象。功能是缓存计算结果(包括React元素这类对象),避免每次组件渲染都重新计算或创建新对象,以此保证引用稳定性。

解决memoIcon的重渲染问题

如果想让memoIcon也能避免触发MemoMenuButton重渲染,有两种简单方式:

  1. 用useMemo缓存memoIcon的引用:
const memoIcon = useMemo(() => <MemoBoldIcon />, []);
  1. 将memoIcon的定义移到BoldButton组件外部(因它不依赖组件内部变量):
const MemoBoldIcon = memo(BoldIcon);
const memoIcon = <MemoBoldIcon />; // 全局仅创建一次

export const BoldButton = () => {
  // ... 组件内部逻辑
};

内容的提问来源于stack exchange,提问作者Ugus

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 15:01:09