zoukankan      html  css  js  c++  java
  • react数据管理

      react的设计思想就是界面由数据驱动,公式:UI = f(data)。UI代表最终渲染的界面,f表示的是一个函数,data就是数据。data可以来自于组件内部的state,也可以是props。就是下文中讲到的内容。

    一、组件状态state
      组件内的数据分为两种
    • state    组件内部数据,外部不可见
    • props  外部传入的数据
       所以,判断一个数据应该放在哪里,用下面的原则:

       1、如果数据由外部传入,放在 props 中;

       2、如果是组件内部状态,是否这个状态更改应该立刻引发一次组件重新渲染?如果是,放在 state 中;不是,放在成员变量中。

      如何修改state:
    1 this.state.foo = 'bar'; //错误的方式 
    2 this.setState({foo:'bar'}); //正确的方式
      如上面代码所示,如果只是修改 this.state,那改了也就只是改了这个对象,其他的什么都不会发生;如果使用 setState 函数,那不光修改 state,还能引发组件的重新渲染,在重新渲染中就会使用修改后的 state,这也就是达到根据 state 改变公式左侧 UI 的目的。
      但是setState并不是每次调用都能触发渲染。React为了优化渲染,避免每次setState都去渲染而浪费性能,用了任务队列的方式来解决,多次setState调用会往队列里放多个任务,然后React会选择合适的时机去处理,当批量处理开始时,会合并多个setState,比如下面:
    1 this.setState({count: 1}); 
    2 this.setState({caption: 'foo'}); 
    3 this.setState({count: 2});

      最终会被合并为this.setState({count: 2, caption: 'foo'});所以被合并后多次的setState只会更新一次,从而只引发一次重新渲染。当然也因为有这个队列的存在setState在React中无法保证同步更新state中的数据。注意:setState中的对象合并都是->浅合并

       state的批处理: 
      可以这么理解,当 React 调用某个组件的生命周期函数或者事件处理函数时,React 会想:“嗯,这一次函数可能调用多次 setState,我会先打开一个标记,只要这个标记是打开的,所有的 setState 调用都是往任务队列里放任务,当这一次函数调用结束的时候,我再去批量处理任务队列,然后把这个标记关闭。”
    (这里可以对应到pendingTime:https://react.jokcy.me/book/update/expiration-time.html
            批处理推荐文章:https://www.jianshu.com/p/7ab07f8c954c
            那么如何进行setState的连续操作并产生同步效果?使用函数式setState
            setState 的第一个参数为函数时,任务列表上增加的就是一个可执行的任务函数了,React 每处理完一个任务,都会更新 this.state,然后把新的 state 传递给这个任务函数。
    1 function increment(state, props) { 
    2     return {count: state.count + 1}; 
    3 }
    4 this.setState(increment); 
    5 this.setState(increment); 
    6 this.setState(increment);

    二、Redux数据管理工具

      Redux相当于是所有组件共享的数据store,打破了父子、子父、兄弟组件之间的数据传递的路径,都可以直接去store里拿。
    适合redux的场景:
    第一步,看这个状态是否会被多个 React 组件共享。
            所谓共享,就是多个组件需要读取或者修改这个状态,如果是,那不用多想,应该放在 Store 上,因为 Store 上状态方便被多个组件共用,避免组件之间传递数据;如果不是,继续看第二步。
     
    第二步,看这个组件被 unmount 之后重新被 mount,之前的状态是否需要保留。
            举个简单例子,一个对话框组件。用户在对话框打开的时候输入了一些内容,不做提交直接关闭这个对话框,这时候对话框就被 unmount 了,然后重新打开这个对话框(也就是重新 mount),需求是否要求刚才输入的内容依然显示?如果是,那么应该把状态放在 Store 上,因为 React 组件在 unmount 之后其中的状态也随之消失了,要想在重新 mount 时重获之前的状态,只能把状态放在组件之外,Store 当然是一个好的选择;如果需求不要求重新 mount 时保持 unmount 之前的状态,继续看第三步。
     
    第三步,到这一步,基本上可以确定,这个状态可以放在 React 组件中了。
     
    主要掌握点
    1. Redux 中的基本概念 action、reducer 和 store;
    2. 使用 react-redux 会应用哪些设计模式;
    3. 如何设计 Redux 的 Store。
     
    三、Mobx数据管理工具
      简单直接的数据操作,不需要做dispatch,不必如redux走一遍严格的范式,调用action就能修改数据。而且适合使用多个store,当然使用configure配置可以禁止直接修改observable数据,只能使用action。
    主要掌握点
    1. Mobx 的基本功能就是“观察者模式”
    2. decorator 是“装饰者模式”在 JavaScript 语言中的实现
    3. Mobx 通常利用 decorator 来使用
    4. 如何利用 mobx-react 来管理 React组件的状态
     
    四、不同方式的对比
      Redux 认为,数据的一致性很重要,为了保持数据的一致性,要求Store 中的数据尽量范式化,也就是减少一切不必要的冗余,为了限制对数据的修改,要求 Store 中数据是不可改的(Immutable),只能通过 action 触发 reducer 来更新 Store。
     
      Mobx 也认为数据的一致性很重要,但是它认为解决问题的根本方法不是让数据范式化,而是不要给机会让数据变得不一致。所以,Mobx 鼓励数据干脆就“反范式化”,有冗余没问题,只要所有数据之间保持联动,改了一处,对应依赖这处的数据自动更新,那就不会发生数据不一致的问题。
     
    主要区别:
    1. Redux 鼓励一个应用只用一个 Store,Mobx 鼓励使用多个 Store;
    2. Redux 使用“拉”的方式使用数据,这一点和 React是一致的,但 Mobx 使用“推”的方式使用数据,和 RxJS 这样的工具走得更近;
    3. Redux 鼓励数据范式化,减少冗余,Mobx 容许数据冗余,但同样能保持数据一致。
    适用场景:
    Mobx 应用小而简单  快速开发
    Redux 大而复杂  需要长期维护
     
      当然随着react的不断更新发展,也有可能出现react内部的数据共享机制。
     
     
  • 相关阅读:
    Python数据结构-链表
    面试题4:替换空格
    面试题3:二维数组中的查找
    2019.12.17基佬出的一道题
    2019.12.17霍格沃兹测试学院一道题
    python_ck01(虚拟环境管理)
    api_DZFPKJ & api_DZFPCX(get_AES_url代码优化)
    cwyth(自动核销代码)
    api_DZFPKJ & api_DZFPCX
    字符串返回数组并排序(算法题)
  • 原文地址:https://www.cnblogs.com/dfzc/p/11404618.html
Copyright © 2011-2022 走看看