Componment存在的问题?
父组件重新render(),当前组件的子组件也会重新执行render(),即使state没有任何变化
当前组件setState(),会重新执行render(),即使state没有任何变化
解决Component存在的问题?
原因: 组件的shouldComponentUpdate ()默认返回true,即使数据没有变化,render()也会重新执行
方法1: 重写 shouldComponentUpdate () 方法,判断数据是否发生变化,发生变化返回true,反之返回false
方法2: 使用PureComponent代替Component
**说明:**一般使用PureComponent来优化组件性能
案例
1、点击 ‘测试-App’ 按钮,App组件和B组件都会重新渲染
2、即使 App组件不向B组件传递数据,B组件也会重新渲染
3、即使App组件中没有数据变化,但是只要使用了 setState({}) B组件也会重新渲染
4、当state和props中的状态都没有更新的时候,不让B组件重新渲染
- 在B组件中使用 shouldComponentUpdate ,代码如下
5、当state和props中的状态都没有更新的时候,不让B组件重新渲染
- 使用PureComponent 代替 Component
- class B extends React.Component 改为 class B extends React.PureComponent
class App extends React.Component {
constructor(props) {
super(props);
this.state = {
m1: 1
}
}
test1 = ()=> {
this.setState(state => ({
m1: state.m1 + 1
}))
this.setState({}); // 这样写B组件也会重新渲染
}
render() {
console.log('render-App');
return (
<div>
<h1>{this.state.m1}</h1>
<button onClick={this.test1}>测试-App</button>
<B m1={this.state.m1} />
</div>
)
}
}
class B extends React.Component {
constructor(props) {
super(props);
this.state = {
m2: 1
}
}
test2 = ()=> {
this.setState(state => ({
m2: state.m2 + 1
}))
}
/**
默认返回true,即使数据没有变化,render()都会重新执行
重写 componentShouldUpdate() 方法,判断数据是否发生变化,发生变化返回true,反之返回false
*/
shouldComponentUpdate(nextProps, nextState) {
// 比较新旧props和state中的数据,如果没有一个变化返回false,返回返回true
if(this.props.m1 === nextProps.m1 && this.state.m2 === nextState.m2) {
return false;
} else {
return true;
}
}
render() {
console.log('render-B');
return (
<div>
<h1>m2={this.state.m2},m1={this.props.m1}</h1>
<button onClick={this.test2}>测试--B</button>
</div>
)
}
}
常见Bug
子组件使用 PureComponent
父组件在更新一个引用数据类型的数据时使用下面的方式:
state = {
m1:{ count:0}
}
click1 = ()=> {
const m1 = this.state.m1;
m1.count = 2;
// 这种写法是错误的,因为m1对象本身并没有发生变化,只是内部的数据发生了变化,
// 所以如果子组件使用的是PureComponent那么子组件是不会更新的
this.setState({m1});
// 下面这种写法是正确的:子组件会被更新
this.setState({m1:[...m1]})
}