react原理篇:组件性能优化(减轻state、使用纯组件PureComponent避免不必要的重新渲染)
目录
二 避免不必要的重新渲染
2.1 基础使用
2.2 随机数案例(使用nextState比较)
2.3 随机数案例(使用nextProps比较)
三 纯组件PureComponent
3.1 纯组件的基本使用
3.2 纯组件原理
一 减轻state
只存储跟组件渲染相关的数据(比如count、列表数据、loading等)
注意:不用做页面渲染的数据不要放在state中(比如定时器、id等),可以放在this中
二 避免不必要的重新渲染
2.1 基础使用
组件更新机制: 父组件更新会引起子组件也被更新(子组件没有任何变化也会重新渲染)
问:如何避免不必要的渲染?
答:用钩子函数shouldComponentUpdate解决(返回true重新渲染,返回false不重新渲染)
→ 该函数属于更新阶段的钩子函数,在组件重新渲染render前执行
完整代码
import React from "react";
import ReactDOM from "react-dom";
class App extends React.Component {
state = {
count: 1
}
fn = () => {
this.setState((state, props) => {
return {
count: state.count + 1
}
}, () => {
console.log("更新的:" + this.state.count)
})
}
shouldComponentUpdate(nextProps, nextState) {
//最新的状态
console.log("nextState:",nextState)
//更新前的状态
console.log("this.state:",this.state)
//返回false 阻止组件重新渲染
return false;
}
render() {
return (
<div>
<p>count:{this.state.count}</p>
<button onClick={this.fn}>点我</button>
</div>)
}
}
ReactDOM.render(<App/>, document.getElementById("root"));
效果
点击按钮3次,state里的count的最新值是4,因为使用了钩子函数shouldComponentUpdate, return 了 false, 所以不重新渲染页面, 所以页面上的count还是1 (备注:this.state里面的count值为3 是因为setState更新数据是异步的,所以count的最新值还没有更新过来)
关于setState异步更新请点这里
把钩子函数shouldComponentUpdate的返回值改为true (允许组件重新渲染),点击按钮三次.页面的count值又恢复了
2.2 随机数案例(使用nextState比较)
实现效果: 当两次生成的随机数不一样的时候才重新渲染页面
import React from "react";
import ReactDOM from "react-dom";
class App extends React.Component {
state = {
number: 0
}
fn = () => {
this.setState(() => {
return {
number:Math.floor(Math.random()*3)
}
})
}
shouldComponentUpdate(nextProps, nextState) {
//最新的状态
console.log("最新的状态:",nextState)
//更新前的状态
console.log("上一次的状态:",this.state)
//当两次生成的随机数是一样的时候,不重新渲染页面
// if(nextState.number===this.state.number){
// return false;
// }
// return true;
//当两次生成的随机数不一样的时候才重新渲染页面
return nextState.number!==this.state.number
}
render() {
console.log("render")
return (
<div>
<p>随机数:{this.state.number}</p>
<button onClick={this.fn}>产生随机数</button>
</div>)
}
}
ReactDOM.render(<App/>, document.getElementById("root"));
效果
2.3 随机数案例(使用nextProps比较)
代码
import React from "react";
import ReactDOM from "react-dom";
class App extends React.Component {
state = {
number: 0
}
fn = () => {
this.setState(() => {
return {
number:Math.floor(Math.random()*3)
}
})
}
render() {
console.log("父组件的render")
return (
<div>
<Box number={this.state.number}/>
<button onClick={this.fn}>产生随机数</button>
</div>)
}
}
class Box extends React.Component{
shouldComponentUpdate(nextProps){
console.log("最新的props:",nextProps,"上一次的props:",this.props)
if(nextProps.number!==this.props.number){
return true;
}
return false;
}
render(){
console.log("子组件的render")
return <p>随机数:{this.props.number}</p>
}
}
ReactDOM.render(<App/>, document.getElementById("root"));
效果
三 纯组件PureComponent
3.1 纯组件的基本使用
为什么要用纯组件?
纯组件内部自动实现了shouldComponentUpdate这个钩子函数,不需要手动比较
使用方法:继承 React.PureComponent
代码
import React from "react";
import ReactDOM from "react-dom";
class App extends React.PureComponent {
state = {
number: 0
}
fn = () => {
this.setState(() => {
return {
number:Math.floor(Math.random()*3)
}
})
}
render() {
return (
<div>
<Box number={this.state.number}/>
<button onClick={this.fn}>产生随机数</button>
</div>)
}
}
class Box extends React.PureComponent{
render(){
console.log("子组件的render")
return <p>随机数:{this.props.number}</p>
}
}
ReactDOM.render(<App/>, document.getElementById("root"));
3.2 纯组件原理