网上的教程看得挺乱的, 还是心愿大家手动打代码, 去体验下, 印象更好
React.memo 和 useMemo 都是缩小组件中不必要的开销, 晋升性能
其中, memo 是子组件自身是否渲染, useMemo 则是子组件 prop 监听函数
memo
memo 很像 shouldComponentUpdate 生命周期还判断组件是否渲染
不应用 memo
const Child = ({name, children}: any) => {function changeName(name: string) {console.log("changeName");
return name + "扭转 name 的办法";
}
console.log("Child 组件更新");
const otherName = changeName(name);
return (
<>
<div>{otherName}</div>
<div>{children}</div>
</>
);
};
function Parent() {const [count, setCount] = useState(0);
const [name, setName] = useState("名称");
return (
<>
<div>{count}</div>
<button id="btn1" onClick={() => setCount(count + 1)}>count</button>
<button id="btn2" onClick={() => setName(new Date().getTime() + "")}>name</button>
<Child name={name}></Child>
</>
);
}
export default Parent;
点击 btn1, btn2 按钮二者都会触发 Child 了, 都会打印
Child 组件更新
changeName
点击 btn1, Child 没用 count 属性却还是渲染了, 所以就有了 memo
批改 Child.tsx
const Child = React.memo(({name, children}: any) => {function changeName(name: string) {return name + "扭转 name 的办法";}
console.log("Child 组件更新");
const otherName = changeName(name);
return (
<>
<div>{otherName}</div>
<div>{children}</div>
</>
);
});
点击 btn1, 就不会在触发 Child 了
useMemo
useMemo 更加具体到组件外部的调用办法
const Child = ({name, children}: any) => {function changeName(name: string) {console.log("changeName");
return name + "扭转 name 的办法";
}
console.log("Child 组件更新");
const otherName = changeName(name);
return (
<>
<div>{otherName}</div>
<div>{children}</div>
</>
);
};
function Parent() {const [name, setName] = useState("名称");
const [content, setContent] = useState("内容");
return (
<>
<button id="btn1" onClick={() => setName(new Date().getTime() + "")}>name</button>
<button id="btn2" onClick={() => setContent(new Date().getTime() + "")}>content</button>
<Child name={name}>{content}</Child>
</>
);
}
点击 btn1, btn2 按钮二者都会触发 Child 了, 都会打印
Child 组件更新
changeName
点击 btn2 的时候, 因为 Child 从新渲染, 所以导致 changeName 也跟着打印了
然而 btn2 只扭转 content, 没扭转 Child 中 changeName 须要的属性 name,
对此, 咱们心愿扭转 content 的时候, 不触发组件中 changeName 函数, 因为 changeName 只应用到 name 属性, 因而咱们应该应用 useMemo
const Child = ({name, children}: any) => {function changeName(name: string) {console.log("changeName");
return name + "扭转 name 的办法";
}
console.log("Child 组件更新");
const otherName = useMemo(() => changeName(name), [name]);
return (
<>
<div>{otherName}</div>
<div>{children}</div>
</>
);
};
但咱们点击 btn2 的时候, 只触发了
Child 组件更新