更新机制
graph TD
JSX --> 虚拟DOM --> 真实DOM
props或state发生改变->render函数被重新执行->产生新的虚拟DOM->新旧DOM进行diff算法->差异更新->更新真实DOM
- 同层节点比较
- 对于不同类型的节点进行直接替换、不会比较子节点
- 列表循环绑定key的diff算法优化
render函数优化
存在问题:setState发生改变会重新执行render函数、即使我只是改了一个初始值、内部的子组件并未发生改变也会重新执行、进行一个整体上的重新渲染。即App组件的render函数重新执行、内部子组件的render函数都会被重新执行一次浪费性能
// SCU优化
// 需要对传入的props有没有改变 or 自己的state前后值有没有变化
shouldComponentUpdate(nextProps, nextState) {
if (this.state.msg !== nextState.msg || this.props.counter !== nextProps.counter) {
return true; // render函数会被重新执行
}
return false;
}
SCU优化
PureComponent
目的:就是为了监听传入的属性和状态state是否有变化,是否需要重新执行render函数提高性能,做的浅能比较
import React, { Component, PureComponent } from "react";
export class App extends Component {}
// 继承PureComponent就实现了性能优化
export class App extends PureComponent {}
// 这个是错误的 PureComponent
this.state.movie.push('海贼王')
this.setState({movie: this.state.movie})
// 正确做法
const movies = [...this.state.movie]
movies.push('一条数据')
this.setState({movie: movies})
memo
目的:类组件可以使用PureComponent进行优化,这样只有组件所依赖的props和state发生改变的时候,rander函数才会被重新执行。而在函数组件里面采用memo包裹
import {memo} from 'react
function Home(props) {
return (
<div>{props.msg}</div>
)
}
// 不包裹的时候只要App组件数据发生变化 整体的render函数就需要重新执行 即使我们没有改变msg的值 浪费性能
const Home = memo(function(props) {
return (
<div>{props.msg}</div>
)
})
export default Home