1、概念
React.memo 为高阶组件。 如果你的组件在相同 props 的情况下渲染相同的结果,那么你可以通过将其包装在 React.memo 中调用,以此通过记忆组件渲染结果的方式来提高组件的性能表现。这意味着在这种情况下,React 将跳过渲染组件的操作并直接复用最近一次渲染的结果。
类似于类组件中的PureComponent,都是浅层比较,只比较第一层的数据。
javascript
import React, { useState, useEffect, useContext } from 'react';
// 如果num不改变当前组件不会重新渲染
const MyComponent = React.memo((props) => {
/* 使用 props 渲染 */
return (
<div>{props.num}</div>
)
})
export default function hook() {
const [num, setNum] = useState(1)
return (
<div>
<button onClick={() => setNum(num + 1)}>+1</button>
<MyComponent num={num}></MyComponent>
</div>
)
}
2、特点
React.memo 仅检查 props 变更。如果函数组件被 React.memo 包裹,且其实现中拥有 useState,useReducer 或 useContext 的 Hook,当 state 或 context 发生变化时,它仍会重新渲染。
3、可接受第二个参数
默认情况下其只会对复杂对象做浅层对比,即只比较第一层的key,shallowEqual主要是通过Object.js来对比,因此对于对象或数组,则为false,因此每次都会进行渲染,如果你想要控制对比过程,那么请将自定义的比较函数通过第二个参数传入来实现,第二个参数是一个函数,返回true不渲染,false渲染
javascript
import React, { useState, useEffect, useContext } from 'react';
const MyComponent = React.memo((props) => {
/* 使用 props 渲染 */
return (
<div>{props.num}</div>
)
/**
* prevProps 上次的值
* nextProps 最新的值
*
* 如果传来的值是偶数的话则不更新组件
*/
}, (prevProps, nextProps) => {
console.log(nextProps, nextProps.num % 2)
return nextProps.num % 2 === 0
})
export default function hook() {
const [num, setNum] = useState(1)
useEffect(() => {
/**
* 当它是一个空数组时,回调只会被触发一次,类似于 componentDidMount
*/
console.log("componentDidmount")
}, [])
return (
<div>
<button onClick={() => setNum(num + 1)}>+1</button>
<MyComponent num={num}></MyComponent>
</div>
)
}