Home.tsx
import React, { ReactElement, useCallback, useMemo, useState } from "react";
import Child from "../../components/Child";
interface HomeProps {}
const Home: React.FC<HomeProps> = ({}): ReactElement => {
const [count, setCount] = useState(0);
const [msg, setMsg] = useState("大内密探零零发");
let personMsg = useMemo(() => {
return {
name: "张强",
};
}, []);
const clickEvent = useCallback(() => {
console.log("点击");
}, []);
return (
<div>
Home--{count}
<div>
<button onClick={() => setCount(count + 1)}>+</button>
</div>
<Child msg={msg} personMsg={personMsg} clickEvent={clickEvent} />
</div>
);
};
export default Home;
Child.tsx
import React, { memo } from "react";
interface ChildProps {
msg: string;
personMsg: any;
clickEvent: ()=> void
}
const Child: React.FC<ChildProps> = memo(({ msg, personMsg, clickEvent }) => {
console.log("ChildRender");
return (
<div>
Child--{msg}
<div>{personMsg.name}</div>
<button onClick={clickEvent}>点击</button>
</div>
);
});
export default Child;
memo()用法:功能类似于class组件的PureComponent,帮助我们做SCU,即:子组件外层包裹memo()后,当父组件状态改变或者props改变的时候,如果子组件所依赖的属性没有发生改变,则子组件不发生re-render。只有父组件中和子组件相关依赖的属性发生改变的时候,子组件才会re-render.
useMemo()用法:必须和memo()结合使用。当父组件中存在一个变量(不是state)且传入子组件,每次父组件re-render的时候,这个变量都会重新构建,从而导致子组件的re-render。这个时候我们可以通过useMemo将变量进行包裹缓存,避免了变量的重新构建导致子组件的重新渲染。
useCallback()用法:必须和memo()结合使用。用法和useMemo()类似,区别是一个对变量进行缓存,一个对内部函数进行缓存。当父组件状态改变的时候,父组件的更新会重新构建其内部函数,如果某个内部函数传入了子组件,那么父组件函数的重新构建则会导致子组件的re-render。这时候则可以使用useCallback()将对应函数包裹,避免了函数的重新构建导致子组件的重新渲染。
useMemo()和useCallback()的第二个参数可以放入某些依赖,当这些依赖发生改变的时候才进行重新构建。
useMemo()还可以用作计算属性,防止组件re-render的时候进行重复的大量计算