页面略微丑陋,是我从为知笔记粘贴过来的, 原文链接
正常情况下,为了减少子组建中没必要的渲染, 一般会在子组建中 使用 React.memo() 进行包裹, 例如
const Child = ({acount}) => {
return (
<button>{acount}</button>
)
}
export default React.Memo(Child)
这种情况下,只要 传入数据 acount 不变化, 子组建就不会重新渲染
**** 父组件有两种情况,
1)当父组建是类组件时候,即使传入子组件的参数中有函数,子组件使用了 React.memo()进行了包裹, 即使父组件重新render, 子也不会更新,
import Child from 'xxx/xxx/Child';
class Index extends React.Component{
constructor(props){
super(props)
state = {
acount: 0
}
}
changeAcount = () => {
const { acount } = this.state;
this.setState({
acount: acount+1
})
}
render() {
const { acount } = this.state;
const { userList = [] } = this.props;
return(
<Button onClick={changeAcount}>+1</Button>
<span>{acount}</span>
<Child userList={userList}/>
)
}
}
// 子组件, 此时没有传入函数, 只是传入了数据,
const Child = ({userList}) => {
return (
<Button>小鱼</Button>
)
}
export default Child;
// 子组件, 参数同时有数据 和 回调函数
const Child = ({userList, deleDemo}) => {
return (
<Button onClick={() => deleDemo()}>小鱼</Button>
)
}
export default Child;
// 这回可以看到, 父组件在重新setState的时候, 子组件依旧不会重新加载
2)当父组件为函数式组件的情况下, 如果传入子组件中有函数, 即使使用了 React.memo() 包裹,也会造成再次没必要的渲染
// 将上面的 父组件改成函数式组建, 就会发现父组件执行 setState的时候, 子组件重新render了
当父组建为函数式组件的时候,为了防止子组件没必要渲染
import React,{ useCallBack } from 'react';
const Index = (props) => {
const changeAcount = () => {
const { acount } = this.state;
this.setState({
acount: acount+1
})
}
// 这里使用了 useCallBack对函数进行了一次包装, 在父组件执行 setState的时候,子组件不会重新渲染, 因为父组件的每次渲染,函数都是一个新的函数,传入组件会被认为新参数,这里的 useCallBack 相当于做了一个函数的缓存, 子组件在接收的时候 认为参数没变
const getNameChild = useCallBack((state) => {
console.log('子组件传入数据', state)
}, [])
render() {
const { acount } = this.state;
const { userList = [] } = this.props;
return(
<Button onClick={changeAcount}>+1</Button>
<span>{acount}</span>
<Child userList={userList} getName={getNameChild}/>
)
}
}
export default Index;