zustand
是一个用于状态管理的简单而强大的库,它可以与 React 一起使用。它提供了一种简单的方式来管理组件的状态,并且遵循了 React Hooks 的使用规范。
使用 zustand
可以方便地创建和共享状态,同时还能够实现状态的订阅和更新。通过 zustand
,你可以创建自定义的状态钩子,并在组件中使用这些钩子来获取状态并进行状态更新。
1.下载、创建、基础用法
npm install zustand
import './App.css'; import {create} from 'zustand' //1.创建store //注意事项: //(1)函数参数必须返回一个对象,对象内部编写状态数据和方法 //(2)set方法是用来修改数据的专门方法 必须调用这个方法来修改数据 //语法1:参数是函数 需要用到老数据的情况 //语法2:参数直接是一个对象 const useStore= create((set)=>{ //create方法内部是一个函数 return { //return一个对象 count : 0, //存储的数据状态 inc : ()=>{ //修改状态 是一个函数 //语法1 set((state)=>({ count : state.count+1 })) //语法2 // set({count : 100}) } } }) //绑定store到组件 function App() { const {count,inc} = useStore() return ( <div className="App"> <button onClick={inc}>{count}</button> </div> ); } export default App;
代码解析:
-
create
方法接受一个函数作为参数,这个函数内部会接收一个名为set
的函数作为参数。set
函数的作用是用来更新状态。 -
在这个函数内部,通过
return
返回了一个对象,这个对象包含了状态变量count
和更新状态的函数inc
。 -
count
是一个存储数据状态的变量,初始值为0
。 -
inc
是一个函数,调用时将会通过set
函数来更新状态。在这个例子中,它使用了函数式更新的方式,接受当前状态state
作为参数,并返回一个新的状态对象,从而实现对count
状态的加一操作。 -
最终,通过
create
方法返回的内容,我们可以在组件中使用useStore
钩子来获取count
状态和inc
函数,并且在组件中进行状态的更新和管理。
2.异步支持
import { useEffect } from 'react'; import './App.css'; import {create} from 'zustand' const URL ='http://xxxxxxs' const useStore= create((set)=>{ //create方法内部是一个函数 return { //return一个对象 channelList : [], asyncGetList : async ()=>{ const res = await fetch(URL) const jsonres = await res.json() console.log(jsonres) set({ channelList : jsonres }) } } }) //绑定store到组件 function App() { const {count,inc ,asyncGetList,channelList} = useStore() useEffect(()=>{ asyncGetList() },[asyncGetList]) return ( <div className="App"> <button onClick={inc}>{count}</button> </div> ); } export default App;
代码解析:
-
create
方法用于创建一个新的 Zustand store。它接受一个回调函数作为参数,该回调函数会接收set
方法作为参数,并返回一个包含状态和操作的对象。 -
在回调函数中,返回一个包含
channelList
和asyncGetList
的对象。channelList
用于存储频道列表,asyncGetList
是一个异步函数,用于从指定的 URL 获取数据并更新channelList
。 -
在组件中使用
useStore
调用create
创建的 Zustand store,获取到asyncGetList
和channelList
。 -
使用
useEffect
钩子在组件挂载后调用asyncGetList
函数,以便获取频道列表数据。在useEffect
的依赖数组中传入asyncGetList
,以确保只有在asyncGetList
函数发生变化时才会重新触发效果。 - 需要注意的是,这段代码中的
URL
变量是一个占位符,实际项目中应该替换为真实的 API 地址。
3.切片模式
import { useEffect } from 'react'; import './App.css'; import {create} from 'zustand' const createCounterStore = (set)=>{ return { count : 0, //存储的数据状态 inc : ()=>{ //修改状态 是一个函数 //语法1 set((state)=>({ count : state.count+1 })) //语法2 // set({count : 100}) }, } } const createChannelStore = (set)=>{ return { channelList : [], asyncGetList : async ()=>{ const res = await fetch(URL) const jsonres = await res.json() console.log(jsonres) set({ channelList : jsonres }) } } } const useStore= create((...a)=>{ //create方法内部是一个函数 return { ...createCounterStore(...a), ...createChannelStore(...a) } }) //绑定store到组件 function App() { const {count,inc ,asyncGetList,channelList} = useStore() useEffect(()=>{ asyncGetList() },[asyncGetList]) return ( <div className="App"> <button onClick={inc}>{count}</button> </div> ); } export default App;
代码解析:
-
createCounterStore
函数用于创建一个存储计数器状态的 store。它接受set
方法作为参数,并返回一个包含计数器状态和增加计数器函数的对象。 -
createChannelStore
函数用于创建一个存储频道列表状态的 store。它同样接受set
方法作为参数,并返回一个包含频道列表和异步获取频道列表数据的函数的对象。 -
在
useStore
中使用create
方法创建一个包含两个不同 store 的 Zustand store。通过使用...
操作符将createCounterStore
和createChannelStore
的返回值合并到同一个对象中。 -
在组件中使用
useStore
调用create
创建的 Zustand store,获取到count
、inc
、asyncGetList
和channelList
。