【拓展】 react 中的 setState
在之前博客中说过 【 react 使用 state 】,其实这一小部分算是那一篇博文的拓展吧!关于修改状态值的相关知识点,但是不是太难的部分,稍微提一嘴。
案例
还是习惯性的以案例开始,我们实现一个简单的案例,写一个组件,这个组件有啥用呢?很简单,点击按钮,数据 +1,然后数据在页面上显示一下。就是下面这个样子:
OK,这个案例在之前博客写了无数遍了,都写烂了,只把关键代码贴进来啦哈!
import React, { Component } from 'react';
export default class Demo extends Component {
state = { count: 0 }
add = () => {
const { count } = this.state
this.setState({ count: count + 1 })
}
render() {
return (
<div>
<h2>当前的数据为:{this.state.count}</h2>
<button onClick={this.add}>点我+1</button>
</div>
);
}
}
好,就是上面这段代码,点击按钮执行 add 方法,add 方法中,首先获取当前状态的 count 值,然后通过 setState 方法更新 count 数据值,实现 count 数据 +1 操作。
对象式的 setState
我们上面的案例和之前博客写的 setState 都是使用的对象式 setState。因为 setState 里面确实传递了一个对象进去的吧!
然后有一个经典的面试题 【请问:react 中 setState() 是同步的还是异步的?】
要想知道是同步的还是异步的,我们打印一下看看就可以了。
add = () => {
const { count } = this.state
this.setState({ count: count + 1 })
console.log("执行完成", this.state.count)
}
代码是从上往下依次执行,那好,this.setState({ count: count + 1 }) 是来实现对 count + 1 操作的代码,执行完我们在下面打印,应该打印出最新的数据对吧?我们刷新页面,只点击一次,页面应该展示1,控制台应该打印1 就对了,看效果:
这个效果就很明显了把,setState() 是一个异步的,它自身会立即执行,但是他里面 react 操作 state 数据的动作确实异步的,所以说可以理解成 setState() 就是一个异步的方法。
那我们怎么来打印一下更新后的数据呢?很简单,异步操作,一般都有回调函数的,其实 setState() 是有异步函数的,但是呢,我们之前一直没有用。
add = () => {
// 对象式的 setState
const { count } = this.state
this.setState({ count: count + 1 }, () => {
console.log("执行完成", this.state.count)
})
}
我们除了 状态改变对象 之外,写一个回调函数,在回调函数里面打印一下 count 的数据:
诶,现在数据就对了吧!so,这个回调是在什么时候会被调用呢?它在状态更新完毕、界面也更新后(render调用后)才被调用。
函数式的 setState
啊哈哈哈哈哈!除了对象式的 setState 之外,还有 函数式的 setState ,这个之前的博客从来没有说过,然后呢简单说一下,使用函数式 setState 的时候,我们传递的不再是一个对象,而是一个函数,函数可以接收两个参数,第一个参数是 state,第二个参数是 props,这个函数要求返回 状态改变对象。
我们把上面的案例使用 函数式 setState 写一下子,其实也很简单,然后我们在使用这个组件的时候传递一个 name ,然后主要是看看 props 能不能接收到。
<Demo name="𝒆𝒅." />
add = () => {
// 函数式的 setState
this.setState((state, props) => {
console.log('====>>> ', state, props)
return { count: state.count + 1 }
})
}
然后我们点击看一下效果哈!
OK,看到效果是和以前一模一样的,点击按钮也可以正常获取到 state 和 props。当然,函数式 setState 也是有回调函数的,和 对象式 setState 是一样用的,都是可选的,想用就用回调,不想用就不用,它的回调也是在状态更新、界面也更新后(render调用后)才被调用。
然后很多宝子可能会问了,在什么时候使用函数式的,什么时候使用对象式的?其实哈,这个没有具体的标准,你喜欢用啥就用啥,我这里为啥说一下,是怕我们之前一直使用的是对象式的,从来没有提到过函数式,如果实际开发过程中遇到别人写的函数式的,怕我们当场懵掉。
总结
setState(stateChange, [callback])对象式的setState- stateChange为状态改变对象(该对象可以体现出状态的更改)
- callback是可选的回调函数, 它在状态更新完毕、界面也更新后(render调用后)才被调用
setState(updater, [callback])函数式的setState- updater为返回stateChange对象的函数。
- updater可以接收到state和props。
- callback是可选的回调函数, 它在状态更新、界面也更新后(render调用后)才被调用。
对象式的 setState 是函数式的 setState 的简写方式 (语法糖)
使用原则: - 如果新状态不依赖于原状态 -----> 使用对象方式。 - 如果新状态依赖于原状态 -----> 使用函数方式。 - 如果需要在setState()执行后获取最新的状态数据,要在第二个callback函数中读取。
【本博文相关代码资料】:我是𝒆𝒅. 的 gitee
好了,今天的内容就到这里,拜拜啦各位宝子们~~