setState

作者: strong9527 | 来源:发表于2018-01-25 16:20 被阅读56次

    参考文章:

    Lucas HC知乎答案

    程墨Morgan知乎专栏

    深入React书

    react官方解释:setState() does not always immediately update the component. It may batch or defer the update until later. This makes reading this.state right after calling setState()a potential pitfall.

    setState的调用到底发生了什么,在调用setState时,react的表现得真的全都是异步的吗?

    setState方法调用

    在调用此方法后,react会将改变的状态放进一个队列中(pending队列),之后调用enqueueUpdate方法判断是否处于批量处理更新模式,如果判断是正确的那么就将组件保存到dirtyComponents中。enqueueUpdate方法判断不是批量更新模式,那么直接就更新state状态。

    [站外图片上传中...(image-7a43f6-1516868303926)]

    可以看到这其中有一个关键就是enqueueUpdate函数的判断,如果判断不是批量更新模式那么setState就是立即更新state的值。

    
    this.setState({val: this.state.val + 1})
    console.log(this.state.val) // 第一次输出
    
    this.setState({val: this.state.val + 1})
    console.log(this.state.val) // 第二次输出
    
    setTimeout(() => {
        this.setState({val: this.state.val + 1})
        console.log(this.state.val) // 第三次输出
        
        this.setState({val: this.state.val + 1})
        console.log(this.state.val) // 第四次输出
    })
    
    

    这四个输出的console分别是 0、0、2、3

    可以看到前两次setState并没有直接改变state的值,而timeOut里面的setState就同步的改变了state的值。所以,直接说setState是异步更新是不严谨的。

    由 React 控制的事件处理过程 setState 不会同步更新 this.state!

    在 React 控制之外的情况, setState 会同步更新 this.state!

    也就是说在react内部自定义事件绑定的事件函数,是异步更新,而用addEventListener或setTimeout非react内部绑定事件函数就是同步更新。

    函数式setState

    顾名思义,也就是setState的参数不再是一个对象,而是一个函数,这样就可以保障setState安全进行批次处理,setState的值就不会出现覆盖现象。

    function incre() {
        return {score: this.state.score + 1}
    }
    
    function handleState() {
        this.setState( incre )
        this.setState( incre )
        this.setState( incre )
    }
    
    函数式setState能够保证,每一次调用incre函数时,之前队列中的state修改结果都已经完成。
    
    

    而函数式setState也并不是完美的,

    function incrementMultiple() {
      this.setState(increment);
      this.setState(increment);
      this.setState({count: this.state.count + 1});
      this.setState(increment);
    }
    
    

    最后的结果count只增加了2,而不是4,因为遇到了传统的setState方式,所以会把之前的函数时setState的修改效果清空。

    相关文章

      网友评论

          本文标题:setState

          本文链接:https://www.haomeiwen.com/subject/olwvaxtx.html