Zustand 简介 #

什么是 Zustand? #

Zustand 是一个轻量级、简洁且强大的 React 状态管理库。它的名字来自德语,意为"状态"。由 Poimandres 团队开发维护,是目前最流行的 React 状态管理解决方案之一。

核心特点 #

text
Zustand 核心特点
├── 极简 API ──────── 只有一个 create 函数
├── 零样板代码 ────── 无需繁琐的配置
├── 优秀性能 ──────── 基于订阅的精确更新
├── TypeScript ────── 开箱即用的类型推断
├── 中间件系统 ────── 灵活的功能扩展
├── 无需 Provider ─── 直接使用,无需包裹组件
└── React 无关 ────── 可在 React 组件外使用

为什么需要状态管理? #

React 状态管理的挑战 #

在 React 应用中,随着应用规模增长,状态管理面临以下挑战:

tsx
// 问题1:Props Drilling(属性透传)
function App() {
  const [user, setUser] = useState(null)
  return <Layout user={user} setUser={setUser} />
}

function Layout({ user, setUser }) {
  return <Sidebar user={user} setUser={setUser} />
}

function Sidebar({ user, setUser }) {
  return <UserProfile user={user} setUser={setUser} />
}

// 问题2:跨组件状态共享困难
function ComponentA() {
  const [theme, setTheme] = useState('dark')
  // ComponentB 如何获取 theme?
}

// 问题3:Context API 性能问题
const ThemeContext = createContext()

function Provider({ children }) {
  const [theme, setTheme] = useState('dark')
  const [user, setUser] = useState(null)
  
  // 任何状态变化都会导致所有消费者重新渲染
  return (
    <ThemeContext.Provider value={{ theme, setTheme, user, setUser }}>
      {children}
    </ThemeContext.Provider>
  )
}

Zustand 的解决方案 #

tsx
// 创建 store
const useStore = create((set) => ({
  user: null,
  theme: 'dark',
  setUser: (user) => set({ user }),
  setTheme: (theme) => set({ theme }),
}))

// 任意组件直接使用
function ComponentA() {
  const theme = useStore((state) => state.theme)
  const setTheme = useStore((state) => state.setTheme)
  // ...
}

function ComponentB() {
  const user = useStore((state) => state.user)
  // 只订阅 user,theme 变化不会触发重渲染
}

// 在 React 外部使用
const { user } = useStore.getState()
useStore.getState().setUser({ name: 'John' })

与其他方案对比 #

Zustand vs Redux #

特性 Zustand Redux
包体积 ~1KB ~7KB
样板代码 极少 大量
学习曲线 平缓 陡峭
中间件 简单 复杂
DevTools 支持 支持
Provider 不需要 必需
tsx
// Redux 实现计数器
// 1. 定义 action types
const INCREMENT = 'INCREMENT'
const DECREMENT = 'DECREMENT'

// 2. 定义 action creators
function increment() {
  return { type: INCREMENT }
}

function decrement() {
  return { type: DECREMENT }
}

// 3. 定义 reducer
function counterReducer(state = { count: 0 }, action) {
  switch (action.type) {
    case INCREMENT:
      return { count: state.count + 1 }
    case DECREMENT:
      return { count: state.count - 1 }
    default:
      return state
  }
}

// 4. 创建 store
const store = createStore(counterReducer)

// 5. Provider 包裹
<Provider store={store}>
  <App />
</Provider>

// Zustand 实现计数器
const useCounterStore = create((set) => ({
  count: 0,
  increment: () => set((state) => ({ count: state.count + 1 })),
  decrement: () => set((state) => ({ count: state.count - 1 })),
}))

Zustand vs Context API #

特性 Zustand Context API
性能 精确更新 整体重渲染
使用方式 简单 需要 Provider
状态共享 灵活 受限于组件树
调试工具
tsx
// Context API 的问题
const AppContext = createContext()

function AppProvider({ children }) {
  const [count, setCount] = useState(0)
  const [theme, setTheme] = useState('dark')
  const [user, setUser] = useState(null)
  
  // 任何状态变化都会触发所有消费者重渲染
  return (
    <AppContext.Provider value={{ count, setCount, theme, setTheme, user, setUser }}>
      {children}
    </AppContext.Provider>
  )
}

// Zustand 的精确更新
const useStore = create((set) => ({
  count: 0,
  theme: 'dark',
  user: null,
  setCount: (count) => set({ count }),
  setTheme: (theme) => set({ theme }),
  setUser: (user) => set({ user }),
}))

// 只订阅 count,其他状态变化不会触发重渲染
function Counter() {
  const count = useStore((state) => state.count)
  return <div>{count}</div>
}

Zustand vs MobX #

特性 Zustand MobX
包体积 ~1KB ~16KB
响应式 手动订阅 自动追踪
不可变性 默认 可选
学习曲线
装饰器 不需要 可选

Zustand 的设计理念 #

1. 极简主义 #

Zustand 的 API 极其简洁,核心只有一个 create 函数:

tsx
import { create } from 'zustand'

const useStore = create((set) => ({
  // 状态
  count: 0,
  // 更新方法
  increment: () => set((state) => ({ count: state.count + 1 })),
}))

2. 无需 Provider #

不同于 Context API 和 Redux,Zustand 不需要 Provider 包裹:

tsx
// 不需要这样
<Provider store={store}>
  <App />
</Provider>

// 直接使用即可
function App() {
  return <Counter />
}

function Counter() {
  const count = useStore((state) => state.count)
  return <div>{count}</div>
}

3. 精确订阅 #

组件只订阅需要的状态,避免不必要的重渲染:

tsx
// 只订阅 count
const count = useStore((state) => state.count)

// 订阅多个状态
const { count, increment } = useStore((state) => ({
  count: state.count,
  increment: state.increment,
}))

// 使用 selector 进行性能优化
const doubleCount = useStore((state) => state.count * 2)

4. 灵活的状态更新 #

支持多种状态更新方式:

tsx
const useStore = create((set) => ({
  count: 0,
  user: { name: 'John', age: 20 },
  
  // 直接设置
  setCount: (count) => set({ count }),
  
  // 基于前一个状态
  increment: () => set((state) => ({ count: state.count + 1 })),
  
  // 部分更新
  setUserName: (name) => set((state) => ({
    user: { ...state.user, name }
  })),
}))

适用场景 #

推荐使用 Zustand 的场景 #

text
✅ 推荐场景
├── 中小型项目 ────── 快速开发,无需复杂配置
├── 需要轻量方案 ──── 包体积敏感的项目
├── TypeScript 项目 ─ 类型支持友好
├── 简单状态共享 ──── 跨组件状态管理
└── 渐进式迁移 ────── 从其他方案迁移

可能需要考虑其他方案的场景 #

text
⚠️ 需要权衡的场景
├── 超大型项目 ────── 可能需要更严格的架构
├── 团队不熟悉 ────── 学习成本考虑
└── 特殊需求 ─────── 需要特定生态支持

Zustand 生态系统 #

text
Zustand 生态系统
├── 核心库
│   └── zustand ─────────── 核心状态管理
├── 中间件
│   ├── persist ─────────── 状态持久化
│   ├── devtools ────────── 开发工具集成
│   ├── immer ───────────── 不可变数据处理
│   └── redux ───────────── Redux 中间件兼容
├── 工具
│   └── zustand-cli ─────── 命令行工具
└── 社区
    ├── zustand-utils ───── 实用工具集
    └── 示例项目 ────────── 各种场景示例

总结 #

Zustand 是一个现代化的 React 状态管理解决方案,它:

  • 极简:API 简洁,学习成本低
  • 高效:精确订阅,性能优秀
  • 灵活:中间件系统,功能可扩展
  • 友好:TypeScript 支持完善

接下来,让我们开始 安装与配置,将 Zustand 集成到你的项目中。

最后更新:2026-03-28