immutable

作者: 泡杯感冒灵 | 来源:发表于2022-03-31 13:06 被阅读0次
    我们知道,在我们使用reducer时,这个函数接收了原始的state作为参数,并且一定不能对这个state进行修改,需要返回一个新的state回去。想要做到这一点,就需要我们时刻警惕保持编码习惯,不去修改state,但是就怕不小心改了,代码会出现异常,而且找不到出错的地方。那么有没有办法把state变为一个不可以被改变的对象,这样我们就不用时刻担心不小心修改了state了。这个时候,我们需要借助immutable.js这个第三方模块。
    immutable.js是一个第三方模块,是facebook团队历时3年开发的,它可以帮助我们生成一个immutable对象,这个对象是不可被改变的
    • 安装npm install immutable / yarn add immutable
    • 引入方法 fromJS,它可以把一个JS对象变为immutable对象。
    import { fromJS } from 'immutable';
    
    const defaultState = fromJS({
        focused:false
    });
    
    • 当我们在reducer里把state转为immutable对象后,再通过state.header.focused这种方法去访问focused这个属性,是不行的。
    // 转immutable对象之前
    const mapStateToProps = (state) => {
        return {
            focused:state.header.focused
        };
    }
    
    // 转immutable对象之后,通过immutable对象的get方法来访问属性
    const mapStateToProps = (state) => {
        return {
            focused:state.header.get('focused')
        };
    }
    
    
    • 同时,当派发了action后,reducer去修改数据的时候,因为state已经变为了immutable对象,这个时候需要借助immutable对象的set方法去修改
    export default (state = defaultState,action) => {
        if(action.type === constants.SEARCH_FOCUS){
            return state.set('focused',true);
            // return {
            //     focuesd:true
            // };
        }
        if(action.type === constants.SEARCH_BLUR){
            return state.set('focused',false);
            // return {
            //     focuesd:false
            // };
        }
        return state
    }
    
    • 表面看set方法是把state对象修改了,但是实际上它的的逻辑是,会结合之前immutable对象的值设置的值,返回一个全新的对象。并没有对原来的数据进行修改。
    总之,如果不借助immutable对象,我们需要借助手动的方法保证state不被修改,这是存在风险的。当我们引入了immutable对象后,数据就不会被直接的被访问和修改了。而是要通过get和set方法去访问和修改。并没有改变原始的state的内容。
    注意,当我们通过state.header.get('focused')访问 focused的时候,state还是一个JS对象,而header才是immutable对象,这个时候,我们需要把state也转为immutable对象,这个时候需要借助 redux-immutable这个第三方工具。
    • 先安装 npm install redux-immutable
    • 再引入
    // 之前我们通过combineReducers 方法去把小的reducer合并为一个reducer
    import { combineReducers } from 'redux';
    
    // 现在 我们通过引入 redux-immutable的combineReducers 方法,来合并的同时,把传入的对象转为 immutable对象
    import { combineReducers } from 'redux-immutable';
    const reducer = combineReducers({
        header:headerReducer
    })
    
    • 当state也转为immutable对象对象后,我们再访问header就不能直接 state.header了 ,需要通过 immutable对象的get方法
    const mapStateToProps = (state) => {
        return {
            focused:state.get('header').get('focused')
        };
    }
    
    // 还有其他写法,通过`getIn()方法`,该方法接收一个数组
    const mapStateToProps = (state) => {
        return {
            // 意思是,取header下边的focused的值
            focused:state.getIn(['header','focused'])
            // focused:state.get('header').get('focused')
        };
    }
    
    

    相关文章

      网友评论

          本文标题:immutable

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