讲师中心 微信公众号
AI工具推荐 视频效率加速

如何在JavaScript中实现状态管理_从单向数据流到Redux模式详解【教程】

夜瑶吖_4802

夜瑶吖_4802

发布时间:2026-01-17 10:49:02

|

680人浏览过

|

来源于php中文网

原创

90%的中小型React应用用useReducer+useContext足够;Redux Toolkit才值得在需时间旅行、服务端同步、复杂中间件或跨组件高频共享状态时评估;派生状态不应进store,而该用useMemo或createSelector计算。

如何在javascript中实现状态管理_从单向数据流到redux模式详解【教程】

JavaScript 中不需要“从单向数据流讲到 Redux 模式”来实现状态管理——真正需要的,是根据场景选对工具,避免过早抽象。

什么时候该自己写 useState + useReducer,而不是引入 Redux?

90% 的中小型 React 应用,useReducer 配合 useContext 就够用了。Redux 的核心价值不在“状态可预测”,而在于:需要时间旅行调试、服务端状态同步、大量中间件(如 redux-thunk 或 redux-saga)、跨多个不相关组件共享且频繁更新的状态。

  • 表单联动、模态框开关、主题切换 → 用 useState 或 useReducer
  • 购物车 + 用户登录态 + 实时通知三者互相影响 → 可考虑 useReducer + 自定义 Hook 封装
  • 需要回放用户操作、离线优先、与后端状态强一致 → 才值得评估 Redux Toolkit(不是原生 Redux)

useReducer 的常见误用:把所有 state 都塞进一个 reducer

这不是单向数据流的问题,是职责混淆。一个 reducer 应该只负责一类逻辑闭环的状态变更,比如 cartReducer 管购物车,authReducer 管登录态,而不是全塞进 appReducer。

错误示例:

立即学习“Java免费学习笔记(深入)”;

const appReducer = (state, action) => {
  switch (action.type) {
    case 'ADD_TO_CART':
      return { ...state, cart: [...state.cart, action.item] };
    case 'LOGIN_SUCCESS':
      return { ...state, user: action.user, isLoggedIn: true };
    case 'NOTIFY':
      return { ...state, notifications: [...state.notifications, action.msg] };
    default:
      return state;
  }
};

问题:任意 action 都可能意外修改其他字段;无法单独测试;reducer 越来越大。

jm-jsjkxyjs02-pzl-803
jm-jsjkxyjs02-pzl-803

查询全球任意城市的实时天气和未来天气预报

下载

推荐做法:拆分 + 组合

const cartReducer = (state, action) => { /* ... */ };
const authReducer = (state, action) => { /* ... */ };
<p>const rootReducer = (state, action) => ({
cart: cartReducer(state.cart, action),
auth: authReducer(state.auth, action),
});

Redux Toolkit 的 createSlice 不是语法糖,它解决了原生 Redux 的三个硬伤

很多人以为 createSlice 只是自动写 action.type 字符串,其实它关键在:immer 支持可变写法、自动合并 reducers 和 extraReducers、内置 createAsyncThunk 处理副作用。

  • 不用再手写 switch 和 return {...state} —— 直接 state.items.push(item)
  • 异步请求不再需要三层 action(PENDING/FULFILLED/REJECTED)手动 dispatch
  • configureStore 默认开启 serializableCheck 和 immutableCheck,提前暴露不可序列化值(如函数、Date)

典型漏掉的配置:

import { configureStore } from '@reduxjs/toolkit';
import { setupListeners } from '@reduxjs/toolkit/query';
<p>const store = configureStore({
reducer: { /<em> ... </em>/ },
middleware: (getDefault) =>
getDefault().concat(yourCustomMiddleware), // 忘加这行,RTK Query 不生效
});</p><p>setupListeners(store.dispatch); // 忘加这行,refetch 等行为不触发

状态管理最容易被忽略的复杂点:派生状态不该进 store

比如「购物车总价」、「已读消息数」、「筛选后的商品列表」——这些是计算结果,不是源状态。放进 Redux store 会导致:重复计算、缓存失效、与原始数据不同步。

正确方式:

  • React 中用 useMemo 或 createSelector(Reselect)缓存派生值
  • Redux Toolkit 中用 createEntityAdapter + getSelectors 自动处理排序/过滤
  • 永远只在 store 里存 cartItems: [{id, qty}],不要存 totalPrice: 129.99

一旦发现某个字段总要和另一个字段一起更新,或者每次都要靠 useEffect 同步它,那它大概率不该是独立 state。

热门AI工具

更多
Lovart
Lovart Hot

一款面向视觉设计创作的AI设计平台,可通过智能体和画布工作流辅助制作海报、Logo、网页、PPT及其他视觉内容。

切问学术

切问学术是一款AI论文写作工具,复旦大学NLP团队推出的AI学术智能体。

LibLibAI
LibLibAI Hot

一款AI视频创作工具,主要用于国内领先的AI创意平台,以海量模型、低门槛操作与“创作-分享-商业化”生态,让小白与专业创作者都能高效实现图文乃至视频创意表达,适合需要提升相关任务效率的用户。

墨刀AI
墨刀AI Hot

一款AI图像与设计工具,主要用于产品经理的专属智能体,适合需要提升相关任务效率的用户。

WorkBuddy

一款AI办公效率工具,主要用于腾讯云推出的AI原生桌面智能体工作台,适合需要提升相关任务效率的用户。

UpDream
UpDream Hot

一款AI视频创作工具,主要用于哔哩哔哩推出的自研AI视频创作工具,适合需要提升相关任务效率的用户。

音述AI
音述AI Hot

一款AI音频处理工具,主要用于音述AI是一个以“用声音述说故事”为核心的 AI 音乐创作与声音分享社区,适合需要提升相关任务效率的用户。

DeepSeek

DeepSeek是一款面向对话、写作、编程和推理场景的AI大模型工具。

豆包大模型

豆包大模型是一款由字节跳动推出的企业级大语言模型服务平台。

相关专题

更多
什么是中间件
什么是中间件

中间件是一种软件组件,充当不兼容组件之间的桥梁,提供额外服务,例如集成异构系统、提供常用服务、提高应用程序性能,以及简化应用程序开发。想了解更多中间件的相关内容,可以阅读本专题下面的文章。

569

2024.05.11

Golang 中间件开发与微服务架构
Golang 中间件开发与微服务架构

本专题系统讲解 Golang 在微服务架构中的中间件开发,包括日志处理、限流与熔断、认证与授权、服务监控、API 网关设计等常见中间件功能的实现。通过实战项目,帮助开发者理解如何使用 Go 编写高效、可扩展的中间件组件,并在微服务环境中进行灵活部署与管理。

584

2025.12.18

ThinkPHP中间件机制与请求拦截处理实践
ThinkPHP中间件机制与请求拦截处理实践

本专题围绕 ThinkPHP 中间件体系展开,深入讲解中间件的定义、注册与执行流程。内容包括全局中间件与路由中间件的区别、请求前后处理逻辑、自定义中间件开发以及权限验证与日志处理应用。通过实际案例,帮助开发者掌握中间件在项目中的核心作用与最佳实践。

398

2026.03.31

switch语句用法
switch语句用法

switch语句用法:1、Switch语句只能用于整数类型,枚举类型和String类型,不能用于浮点数类型和布尔类型;2、每个case语句后面必须跟着一个break语句,以防止执行其他case的代码块,没有break语句,将会继续执行下一个case的代码块;3、可以在一个case语句中匹配多个值,使用逗号分隔;4、Switch语句中的default代码块是可选的等等。

1031

2023.09.21

Java switch的用法
Java switch的用法

Java中的switch语句用于根据不同的条件执行不同的代码块。想了解更多switch的相关内容,可以阅读本专题下面的文章。

1357

2024.03.13

js 字符串转数组
js 字符串转数组

js字符串转数组的方法:1、使用“split()”方法;2、使用“Array.from()”方法;3、使用for循环遍历;4、使用“Array.split()”方法。本专题为大家提供js字符串转数组的相关的文章、下载、课程内容,供大家免费下载体验。

1558

2023.08.03

js截取字符串的方法
js截取字符串的方法

js截取字符串的方法有substring()方法、substr()方法、slice()方法、split()方法和slice()方法。本专题为大家提供字符串相关的文章、下载、课程内容,供大家免费下载体验。

2264

2023.09.04

java基础知识汇总
java基础知识汇总

java基础知识有Java的历史和特点、Java的开发环境、Java的基本数据类型、变量和常量、运算符和表达式、控制语句、数组和字符串等等知识点。想要知道更多关于java基础知识的朋友,请阅读本专题下面的的有关文章,欢迎大家来php中文网学习。

5784

2023.10.24

Buffalo框架数据库开发全教程
Buffalo框架数据库开发全教程

本专题围绕Buffalo框架数据库开发,讲解database.yml多环境配置、soda与fizz迁移生成回滚、模型结构体标签、增删改查与条件查询、一对多与多对多关联、数据校验、回调钩子、事务处理及原生SQL执行能力。

80

2026.09.23

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
React 教程
React 教程

共58课时 | 12万人学习

国外Web开发全栈课程全集
国外Web开发全栈课程全集

共12课时 | 1.4万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn