Redux和react-redux用法
看到很多小伙伴一见到redux就头疼,笔者今天就来说说这个redux吧。
redux及其中间件介绍,参考:https://blog.csdn.net/lilygg/article/details/118256153
一、redux是什么?
redux是一个专门做状态管理的js库(不是react插件库),它可以用在react,angular、vue等项目中,但基本与react配合使用。
所以说react不是一个完整的框架。而我们所熟知的vuex就很不一样,它只能用在vue里,是vue自己的状态管理工具库,所以vue是一个完整的框架。
作用:集中式管理react应用中多个组件共享状态
二、什么情况下使用redux
某个组件的状态,需要让其他组件可以随时拿到(共享)
一个组件需要改变另一个组件的状态(通信)
总体原则:能不用就不用,如果不用比较吃力才考虑使用
Redux三大原则(action,reducer,store):单一数据源、State是只读的、使用纯函数来执行修改。
Redux用法真没啥复杂的,简单的说吧,
Redux是一个js库,通过里边的createStore(reducer)可以生成一个store,把它导出来就可以在组件里边使用。组件需要更改数据,只需要store.dispatch({action:xx,payload:nnn})派发这样一个动作即可。
这个动作一旦被派发,就会触发reducer函数。reducer是个无副作用的纯函数。它接收两个参数:数据初始值(旧的state)和action对象,返回新的state。
在reducer纯函数里会根据action.type去做不同的数据更改操作,最终返回一个最新的状态,而不是直接更改原始数据。、
以上就是redux的基本工作流程。
在组件更改了数据之后,想要做到实时同步(实时更新数据),需要开发者手动调用store.subscribe(()=>{ //在需要拿redux数据的地方进行数据拿取操作}),实时监听store仓库中数据的变化。
想要拿到redux里的xxx数据,可以通过store.getState().xxx拿到数据xxx。
好了,光说不练假把式,大家也是看得云里雾里,废话不多说,talk is cheap,show me your code.
示例代码:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<!-- 页面演示 -->
<button id="increment">+</button>
<span id="count">0</span>
<button id="decrement">-</button>
<!-- 直接把redux包拔下来引入 -->
<script src="./redux.min.js"></script>
<script>
var initialState = {
count:1
}
function reducer(state=initialState,action){//action是构建redux时定义好的操作
switch (action.type) {
case 'incrementAction':
return {...state,count:state.count+1}
case 'decrementAction':
return {...state,count:state.count-1}
default:
return state;
}
return state;
}
//创建状态
var store = Redux.createStore(reducer);
//获取redux状态中的值
console.log(store.getState());//{count:1}
//添加点击事件
document.getElementById('increment').addEventListener('click',(res) => {
store.dispatch({type:'incrementAction'})
});
document.getElementById('decrement').addEventListener('click',(res) => {
store.dispatch({type:'decrementAction'})
});
//监听redux状态值的变化
store.subscribe(() => {
//把状态中的值注入到dom中
document.getElementById('count').innerText=store.getState().count;
})
</script>
</body>
</html>
上面的是简单版redux用法。
createStore(reducer)是基础用法,createStore函数其实可以有俩参数,下面我们看一下通常在项目中的写法:
import {legacy_createStore as createStore,combineReducers,compose, applyMiddleware} from "redux";
import thunk from "redux-thunk";
const initState = {
a:1
};
function reducer(state = initState,action){
const {type,payload} = action;
switch(type){
case "INIT_DATA":
return state+payload;
default:
return state;
}
}
const devtool = window.__REDUX_DEVTOOLS_EXTENSION__ && window.__REDUX_DEVTOOLS_EXTENSION__();
const store = createStore(
combineReducers({reducer}),
compose(applyMiddleware(thunk),devtool)
);
export default store;
注意:在最新版的redux里,createStore函数已经被legacy_createStore替代。
react-redux是react提供的一个redux辅助js库,能让我们更简单地使用redux。
- redux是redux本包!
- react-redux是负责链接React和Redux的调料包!
前面我们说过,要想达到数据实时变化,需要开发者手动调用suscribe(()=>{})。react-redux则是在此基础上简化了redux用法,不再需要用户手动suscribe(()=>{})监听数据以达到实时变化。
react-redux提供了主要提供了Provider组件传值和connect高阶函数串联我们的组件。connect函数创建的是容器组件,UI组件不直接操作state。
需要传值的组件外部可以直接套个Provider,把store传递过去。就像下面这样:
// src/index.js
// 使用Provider组件注入store
import { Provider } from 'react-redux'
import store from './store'
const root = ReactDOM.createRoot(document.getElementById('root'))
root.render(
<React.StrictMode>
<Provider store={store}>
<App />
</Provider>
</React.StrictMode>
)
导出的组件如果想要包装一下啊,你就调用connect函数。
// HelloWorld.js import React from 'react' // 引入connect函数创建容器组件,ui组件不直接操作state import { connect } from 'react-redux' const HelloWorld = props => { return ( <div> <div>HelloWorld,{props.value}</div> <button onClick={() => props.add(1)}>按钮</button> </div> ) } // 设置给UI组件展示的参数 const mapDispatchToProps = store => { return { value: store, } } // 设置给UI组件调用的方法 const MapDispatchToPropsNonObject = { add: payload => ({ type: 'add', payload }), } export default connect( mapDispatchToProps, MapDispatchToPropsNonObject )(HelloWorld)
以上就是redux和react-redux的基本用法。
好了,代码在于运动,生命在于呼吸。编程使我快乐,欢迎留言和互相交流,欢迎互粉!
本文参考:https://www.jianshu.com/p/cbe5347a61bc

浙公网安备 33010602011771号