React: setState解析

作用

更新 State 中的数据

因为 React 不允许直接更改 state 中的数据,所以引入了 setState() 方法。当调用 setState 时,会重新执行 render 函数,进而根据最新的 State 来创建 ReactElement 对象,以此实现对 DOM 的更新

这是用于更新用户界面以响应事件处理器和处理服务器数据的主要方式

用法

setState(updater, callback)

通过 this.setState() 进行调用

setState 异步更新

constructor(props) {
     
  super(props);

  this.state = {
     
    message: "Hello World"
  }
}

changeState(){
     
  this.setState({
     
    message: 'Hello React'    
  })
  console.log(this.state.message) // Hello World
}

这段代码最终打印出 Hello React

证明 setState() 是异步操作,并不能立即更新 state 中的数据

优点: 可以显著提升性能

如果每次调用 setState 都进行一次更新,那么意味着 render 函数会被频繁调用,界面重新渲染,非常影响效率,所以选择获取到多个更新之后进行批量更新

缺点: 数据无法保持同步

在开发中会产生许多问题

如何获取更新后的值:

  1. 通过 setState() 第二个参数–回调函数获取,该回调函数会在更新后立即执行
changeState = () => {
     
  this.setState({
     
    message: 'Hello React'    
  }), () => {
     
    console.log(this.state.message) // Hello React
  }
}

但这种貌似有些麻烦,一般使用下面这种方法

  1. 使用 asyncawait 获取
changeState = async () => {
     
  await this.setState({
     
    message: 'Hello React' 
  )
  console.log(this.state.message) // Hello React
}
  1. 通过生命周期函数获取
componentDidUpdate(prevProps, provState, snapshot) {
     
  console.log(this.state.message) // Hello React
}

setState 一定是异步吗?

进行如下验证:

  1. setTimeout 中更新
changeState() {
     
  setTimeout(() => {
     
    this.setState({
     
      message: 'Hello React'
    });
    console.log(this.state.message); // Hello React
  }, 0);
}

但是这种方法在 setTimeout 外部还是无法获取更新后的 state 的值

  1. 原生事件中更新
componentDidMount() {
     
  const btn = document.getElementById("btn");
  btn.addEventListener('click', () => {
     
    this.setState({
     
      message: 'Hello React'
    });
    console.log(this.state.message); // Hello React
  })
}

这种方法可以在任何地方获取更新后的 state 的值

通过验证,发现 setState 并不是一定异步的

分为两种情况:

  • 在组件生命周期或 React 合成事件中,setState 是异步
  • setTimeout 或者原生 DOM 事件中,setState 是同步

你可能感兴趣的:(React,react,前端,javascript,reactjs)