复用组件
在协调阶段,组件复用必须满足的三个条件:同一层级下,同一个类型,同一个key值 常见错误: Math.random()或者index做key值
减少组件的重新render
组件重新render会导致组件进入协调,协调的核心就是我们常说的vdom diff,所以协调本身是非常耗时的算法。因此如果能够减少协调,复用旧的fiber节点,那么肯定会加快渲染完成的速度。组件如果没有进入协调阶段,我们称之为进入bailout阶段,意思就是这层组件退出更新
-
shouldComponentUpdate: 类组件的生命周期,当用户定义的这个函数返回false,则进入bailout阶段
-
PureComponent: 更新前会自动比较props与state是否改变,如果两者都没变,则进入bailout阶段
-
memo: 用户可以自定义,默认使用浅比较,比较组件更新前后的props是否相同,如果相同,则进入bailout阶段
const compareFn = (prev, next)=>{ return prev.item === next.item } const Children = (item)=>{return <h1>{item}</h1`>} export default memo(Children,compareFn) // memo的第二个参数是可选项,是一个比较函数 -
useMemo可以缓存参数,useCallback(fn,deps)缓存的是函数,相当于useMemo(()=>fn,deps)
// useMemo缓存的是sum结果,只有当count改变的时候sum才会变 const expensive = useMemo(()=>{ let sum = 0 for(let i=0; i<count; i++){ sum + =i } return sum },[count])// 虽然childComp用了pureComponent会进行浅比较,但是addClick是个函数,每次执行的时候引用地址都是不一样的,这时可以用useCallback把addClick的引用存起来,count变化的时候引用再变 export default function CallbackPage(props){ const addClick = useCallback(()=>{ let sum = 0 for(let i=0; i<count; i++){ sum + =i } return sum },[count]) return( <div> …… <ChildComp addClick = {addClick} /> </div> ) } class ChildComp extends PureComponent(props){ .... } -
Context:Context本身就是一旦Provider传递的value变化,所有监听这个