useReducerはReactのHookのひとつで、useStateに比べてより複雑なコンポーネントの状態管理を可能にします。簡単な利用例は「+」「-」「リセット」ボタンがあり、数字の加算・減算・リセットを管理するようなときになります。
useReducerとuseStateの違い
useReducer | useState | |
定義式 |
| const [state, setState] = useState(initialState); |
実装 | 関数の定義時に更新の方法を決める。 | 値の変更をしたいときに更新の方法を決める。 |
利用ケース | 複数の状態・複雑なロジック管理 | シンプルな状態管理 |
const [state, dispatch] = useReducer(reducer, initialState);
- 左辺のstateは現在の状態
- 左辺のdispachはreducerを実行するための関数
- 右辺のreduerはstateを更新すための関数。state とactionを受け取り、新しいsteteを返す
- 右辺のinitialStateはstateの初期値をセット
- 右辺には省略可能な第三引数 init もある。これは初期stateを返す。指定されていない場合はinitialSateになる。
useReducerを使ったカウンターの実装例
下記のような簡単なカウンターを作ってみます。加算・減算・5ずつ加算・クリアの4つのボタンを作り、ボタンを押すと上のカウントの表示が変化します。
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 |
import { useReducer } from "react"; const reducer = (prev, { type, plusNum }) => { switch (type) { case "plus": return ++prev; case "minus": return --prev; case "addNum": return prev + plusNum; case "clear": return 0; default: throw new Error("actionを正しく設定してください。"); } }; const Sample = () => { const [state, dispatch] = useReducer(reducer, 0); const countUp = () => { dispatch({ type: "plus" }); }; const countDown = () => { dispatch({ type: "minus" }); }; const countPlusNum = () => { dispatch({ type: "addNum", plusNum: 5 }); }; const countClear = () => { dispatch({ type: "clear" }); }; return ( <> <p>カウント: {state}</p> <button onClick={countUp}>+</button> <button onClick={countDown}>-</button> <button onClick={countPlusNum}>+5</button> <button onClick={countClear}>クリア</button> </> ); }; export default Sample; |
const reducer = (prev, { type, plusNum }) => {} の形でreducerの中身を記述します。
第一引数「prev」は前の値
第二引数は「dispachタイプ, 任意のプロパティ」になっています。今回は任意のプロパティは加算する数が入っています。1を加算・減算するのはprev+1やprev-1で計算し、2以上の数を加算するときはplusNumに数字を設定しています。
reducerでは「現在の値(前の値)」「dispatchタイプ」「任意のプロパティ(値)」を受け取りcase文で処理して値を返します。
処理のまとめ
- 1.発火点を作る(今回はボタンのonClick)
- 2.発火点に対応する関数を作る dispatch{(type : ” “)} を実行。
- 3.reducer関数で前の値を変更する処理を実行
- 4.stateが新しい値に更新される