一旦父组件渲染,因此子组件都要跟着渲染,尽管这个子组件并无任何改变。在这种状况下,这个子组件的渲染就变得多余。数组
举个例子🌰:bash
class Child extends Component {
render() {
console.log('Child Render!');
return (
<div>
hello Child!
</div>
);
}
}
class Father extends Component {
state = {
count: 1
}
render() {
console.log('Father Render!');
return (
<div>
<div>count: {this.state.count}</div>
<button onClick={() => this.setState((state) => ({count: state.count + 1}))}>up 1</button>
<Child/>
</div>
);
}
}
export default Father;
复制代码
当点击按钮的时候,改变了父组件的state的值,父组件理所固然的会从新渲染,可是子组件并无使用父组件的state的值,最后却也跟着从新渲染了!函数
浪费资源!ui
给Child组件改变shouldComponentUpdate
生命周期。this
由于没有接受到父组件的props以及自身也没有state,因此直接返回false。spa
若是shouldComponentUpdate
返回false,那么就不会触发该组件的render渲染!code
class Child extends Component {
shouldComponentUpdate(nextProps, nextState, nextContext) {
return false;
}
render() {
console.log('Child Render!');
return (
<div>
hello Child!
</div>
);
}
}
复制代码
因此咱们能够自定义这个shouldComponentUpdate
生命周期来控制组件是否渲染。对象
可是每次这样写着都很麻烦,因而PureComponent就出世了!生命周期
因此PureComponent就用来解决子组件的没必要要渲染问题!内存
class Demo extends PureComponent{
...
}
复制代码
class Demo extends React.PureComponent{
...
}
复制代码
根据上面的例子🌰:
class Child extends PureComponent {
render() {
console.log('Child Render!');
return (
<div>
hello Child!
</div>
);
}
}
class Father extends Component {
state = {
count: 1
}
render() {
console.log('Father Render!');
return (
<div>
<div>count: {this.state.count}</div>
<button onClick={() => this.setState((state) => ({count: state.count + 1}))}>up 1</button>
<Child/>
</div>
);
}
}
export default Father;
复制代码
点击按钮的时候,发现只有父组件渲染了,子组件没有渲染!
PureComponent只能class用,由于函数组件没有shouldComponentUpdate
生命周期!
可是函数组件也是会随着父组件的渲染而渲染的。
memo出世!
上面的例子🌰:
const Child = () => {
console.log('Child Render!')
return <div>hello child</div>
}
const MemoChild = memo(Child);
class Father extends Component {
state = {
count: 1
}
render() {
console.log('Father Render!');
return (
<div>
<div>count: {this.state.count}</div>
<button onClick={() => this.setState((state) => ({count: state.count + 1}))}>up 1</button>
<MemoChild/>
</div>
);
}
}
复制代码
就是他们的对于props和state的比较是浅对比
浅对比:对象就对比他们的内存地址,只要内存地址一致,就不从新渲染,反之,对象的内存地址不一致,就渲染!
因此当面对修改对象数值的时候最好建立一个新对象从新赋值,这样可以起到渲染的做用!
memo对函数组件里面的useState/useContext是不起效的。
意思是context更新了,尽管用了memo,该函数组件依旧会从新渲染。
首先,memo里是没有shouldComponentUpdate这个生命周期的,只是有一个相似的做用。
memo这个函数能够传递两个参数,一个是咱们的组件,一个是相似shouldComponentUpdate这种判断是否渲染的方法。
memo(ChildComponent,()=>{...})
复制代码
不过,值得注意的是,这个方法与shouldComponentUpdate相反:若是返回的是true,那么表示不从新渲染,若是返回的是false,那么要从新渲染。