• React Redux


    React Redux是Redux的官方React UI绑定层。它允许您的React组件从Redux存储读取数据,并将操作分派到存储以更新状态。redux是一个管理状态数据state的容器。提供了可预测的状态管理。

    React Redux 8.x需要React 16.8.3或更高版本/Rect Native 0.59或更高,才能使用React Hooks

    安装

    npm install react-redux
    # Or
    yarn add react-redux
    

    Store
    就是把它们联系到一起的对象。Store 有以下职责:
    维持应用的 state;
    提供 getState() 方法获取 state;
    提供 dispatch(action) 方法更新 state;
    通过 subscribe(listener) 注册监听器;
    通过 subscribe(listener) 返回的函数注销监听器。

    三大原则

    1、单一数据源
    整个应用的 state 被储存在一棵 object tree 中,并且这个 object tree 只存在于唯一一个 store 中。
    2、State 是只读的
    唯一改变 state 的方法就是触发 action,action 是一个用于描述已发生事件的普通对象。
    3、使用纯函数来执行修改
    为了描述 action 如何改变 state tree ,你需要编写 reducers。

    action
    所有数据的变化,必须通过派发(dispatch )action来更新
    action是一个普通的JavaScript对象,用来描述这次更新的type和content;
    使用action的好处是能够知道数据发生了什么变化,数据变化都是可以追踪,可预测的

    reducer
    联系state和action的一个纯函数,不能产生副作用,将传入的state和action结合起来生成一个新的state

    redux 基本使用
    安装redux,使用命令:yarn add redux

    const initialState = {
    	counter :0
    }
    // reducer
    function reducer(state = initialState,action){
    	switch(action.type){
    		case:"INCREMENT":
    			return {...state,counter:state.counter+1};
    		case:"DECREMENT":
    			return {...state,counter:state.counter-1};
    		case:"ADD_NUMBER":
    			return {...state,counter:state.counter+action.num};
    		case:"SUB_NUMBER":
    			return {...state,counter:state.counter-action.num};
    		defaultreturn state;
    	}
    }
    
    // store 创建时要求传入reducer
    const store = redux.createStore(reducer);
    
    // actions
    const action1 = {type:"INCREMENT"};
    const action2 = {type:"DECREMENT"};
    const action3 = {type:"ADD_NUMBER",num:3};
    const action4 = {type:"SUB_NUMBER",num:3};
    //派发action ,派发之后执行reducer
    store.dispatch(action1);
    store.dispatch(action2);
    store.dispatch(action3);
    store.dispatch(action4);
    

    优化,真实开发中我们不可能把所以代码放一起,不方便维护,这里只是基本的使用。

    Provider

    API概述React Redux包括一个<Provider/>组件,该组件使Redux store可用于应用程序的其余部分:

    import React from 'react'
    import ReactDOM from 'react-dom/client'
    
    import { Provider } from 'react-redux'
    import store from './store'
    
    import App from './App'
    
    // As of React 18
    const root = ReactDOM.createRoot(document.getElementById('root'))
    root.render(
      <Provider store={store}>
        <App />
      </Provider>,
    )
    

    Hooks

    React Redux提供了一对自定义React挂钩,允许您的React组件与Redux store 交互。
    useSelector从存储状态中读取一个值并订阅更新,
    useDispatch返回存储的调度方法以允许您调度操作。

    import React from 'react'
    import { useSelector, useDispatch } from 'react-redux'
    import {
      decrement,
      increment,
      incrementByAmount,
      incrementAsync,
      selectCount,
    } from './counterSlice'
    import styles from './Counter.module.css'
    
    export function Counter() {
      const count = useSelector(selectCount)
      const dispatch = useDispatch()
    
      return (
        <div>
          <div className={styles.row}>
            <button
              className={styles.button}
              aria-label="Increment value"
              onClick={() => dispatch(increment())}
            >
              +
            </button>
            <span className={styles.value}>{count}</span>
            <button
              className={styles.button}
              aria-label="Decrement value"
              onClick={() => dispatch(decrement())}
            >
              -
            </button>
          </div>
          {/* omit additional rendering output here */}
        </div>
      )
    }
    

    案例

    利用 react-redux 构建全局状态管理
    ● 创建 reducer,在的数里面判断action的type属性,然后返回状态
    ● 利用 createStore 来捣建 store
    ● 在 App,js 中导入 store
    ● 在 App.js 中导入 Provider,在根组件上对整个结构进行包裹,然后设置 store 属性,来统一对 store进行管理

    App.js

    import LayOut from './pages/LayOut.jsx';
    import store from "./store";
    import { Provider } from 'react-redux';
     
    function App() {
      return ( 
        <Provider store={store}>
          <div className="App"> 
            <LayOut />
          </div>
        </Provider>  
      );
    } 
    export default App;
    

    LayOut 组件 ,pages/LayOut.jsx
    使用useDispatch, useSelector 这两个hooks api 发送提交数据和获取响应的数据

    import React from "react";
    import { useCallback, useEffect } from "react";
    import { setUserInfoAction } from "../store/user/action";
    import { useDispatch, useSelector } from "react-redux";
    
    const LayOut = () => {
        const dispatch = useDispatch()
        const setUserInfo = useCallback((info) => dispatch(setUserInfoAction(info)), [dispatch])
    
        const userInfo = useSelector((state) => state.user);
        const onFinish = () => {
            setUserInfo({
                name: "张三",
                age: "23"
            });
        }
        useEffect(() => {
            console.log(userInfo)
    
        }, [userInfo]);
        return <div>
            登录 保存 user info <br />
    
            {userInfo?.name} -- {userInfo?.age} <br />
            <button onClick={onFinish}>登录</button>
        </div>
    }
    export default LayOut 
    // export default connect(   mapState,  mapDispatch   )(MyComponent)
    

    在src 下新建 store 文件如下 (getter/user.js 不需要)
    在这里插入图片描述
    store 下面的index,js

     import {combineReducers,createStore} from 'redux'; 
     import UserReducer from "./user/reducer"; 
     const reducer = combineReducers({ 
      user: UserReducer,  
    }); 
    const store = createStore (
      reducer
    ); 
    export default store; 
    

    store 下的 user 模块 下的 action.js

    import * as ActionTypes from "./actionTypes";  
    export const setUserInfoAction = (info) => ({
      type: ActionTypes.SET_USERINFO,
      info,
    }); 
    export const clearUser = () => ({
      type: ActionTypes.CLEAR_USERINFO,
    });
    
    

    store 下的 user 模块 下的actionTypes.js

    export const SET_USERINFO = "SET_USERINFO";
    export const CLEAR_USERINFO = "CLEAR_USERINFO";
    

    store 下的 user 模块 下的reducer.js

    
    import * as actionTypes from "./actionTypes";
    const initState = {
        name:"",
        age:""
    }
    
    export default function reducer(state = initState, action) {
      const { type, info } = action
      switch (type) {
        case actionTypes.SET_USERINFO:
          console.log(info)
          return info
        case actionTypes.CLEAR_USERINFO: {
          return null
        }
        default:
          return state
      }
    }
    

    用例结果
    在这里插入图片描述

  • 相关阅读:
    深入了解线程:并发编程的核心要点和应用
    Spring Boot集成Swagger接口分类与各元素排序问题
    【计算机网络笔记】网络层服务与核心功能
    map转list对象方法,通过stream或者iterator.key集合转list,values集合转list
    使用vue-cli创建Vue工程化项目及单文件组件的创建和调用
    docker命令整理
    ffmpeg命令分析-yuv封装mp4
    除了走路,40-60岁的人,还可以进行哪些运动?3种运动可供参考
    【Head First 设计模式】-- 策略模式
    宁波效实中学国际课程与交流中心IB数学课程介绍
  • 原文地址:https://blog.csdn.net/weixin_43506403/article/details/129360440