๋ณธ๋ฌธ ๋ฐ”๋กœ๊ฐ€๊ธฐ
ํ”„๋ก ํŠธ์—”๋“œ/React

useReducer

by alswlfl 2022. 11. 24.

useReducer

  • ์ƒํƒœ ๊ด€๋ฆฌ hook์ค‘ ํ•˜๋‚˜(useState์ฒ˜๋Ÿผ)
  • ์ปดํฌ๋„ŒํŠธ์˜ ์ƒํƒœ ์—…๋ฐ์ดํŠธ ๋กœ์ง์„ ์ปดํฌ๋„ŒํŠธ์—์„œ ๋ถ„๋ฆฌ ๊ฐ€๋Šฅ → ์ƒํƒœ ์—…๋ฐ์ดํŠธ ๋กœ์ง์„ ์ปดํฌ๋„ŒํŠธ ๋ฐ”๊นฅ์— ์ž‘์„ฑ ๊ฐ€๋Šฅ, ์‹ฌ์ง€์–ด ๋‹ค๋ฅธ ํŒŒ์ผ์— ์ž‘์„ฑ ํ›„ ๋ถˆ๋Ÿฌ์™€์„œ ์‚ฌ์šฉ ๊ฐ€๋Šฅ

reducer: ํ˜„์žฌ ์ƒํƒœ์™€ ์•ก์…˜ ๊ฐ์ฒด๋ฅผ ํŒŒ๋ผ๋ฏธํ„ฐ๋กœ ๋ฐ›์•„์™€์„œ ์ƒˆ๋กœ์šด ์ƒํƒœ๋ฅผ ๋ฐ˜ํ™˜ํ•ด์ฃผ๋Š” ํ•จ์ˆ˜

function reducer(state, action) {
	// ์ƒˆ๋กœ์šด ์ƒํƒœ๋ฅผ ๋งŒ๋“œ๋Š” ๋กœ์ง
	// const nextState = ...
	return nextState;
}
  • ๋ฐ˜ํ™˜ํ•˜๋Š” ์ƒํƒœ๋Š” ๊ณง ์ปดํฌ๋„ŒํŠธ๊ฐ€ ์ง€๋‹ ์ƒˆ๋กœ์šด ์ƒํƒœ๊ฐ€ ๋จ
  • action์€ ์—…๋ฐ์ดํŠธ๋ฅผ ์œ„ํ•œ ์ •๋ณด๋ฅผ ์ง€๋‹ˆ๊ณ  ์žˆ์Œ(๊ฐ์ฒด์˜ ํ˜•ํƒœ๋Š” ์ž์œ ) → type ๊ฐ’์„ ์ง€๋‹Œ ๊ฐ์ฒด ํ˜•ํƒœ๋กœ ์‚ฌ์šฉ
//์นด์šดํ„ฐ์— 1์„ ๋”ํ•˜๋Š” ์•ก์…˜
{
	type: 'INCREMENT'
}
//์นด์šดํ„ฐ์— 1์„ ๋นผ๋Š” ์•ก์…˜
{
	type: 'DECREMENT'
}
//input ๊ฐ’์„ ๋ฐ”๊พธ๋Š” ์•ก์…˜
{
	type: 'CHANGE_INPUT',
	key: 'email',
	value: 'tester@react.com'
}
//์ƒˆ ํ•  ์ผ์„ ๋“ฑ๋กํ•˜๋Š” ์•ก์…˜
{
	type: 'ADD_TODO',
	todo: {
		id: 1,
		text: 'useReducer ๋ฐฐ์šฐ๊ธฐ',
		done: false,
	}
}

useReducer ์‚ฌ์šฉ๋ฒ•

const [state, dispatch] = useReducer(reducer, initialState);

  • state: ์ปดํฌ๋„ŒํŠธ์—์„œ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋Š” ์ƒํƒœ๋ฅผ ๊ฐ€๋ฆฌํ‚ด
  • dispatch: ์•ก์…˜์„ ๋ฐœ์ƒ์‹œํ‚ค๋Š” ํ•จ์ˆ˜ → dispatch({type: ‘INCREMENT’})
  • ์ฒซ ๋ฒˆ์งธ ํŒŒ๋ผ๋ฏธํ„ฐ: reducer ํ•จ์ˆ˜
  • ๋‘ ๋ฒˆ์งธ ํŒŒ๋ผ๋ฏธํ„ฐ: ์ดˆ๊ธฐ ์ƒํƒœ
import React, { useReducer } from "react";

function reducer(state, action) {
  switch (action.type) {
    case "INCREMENT":
      return state + 1;
    case "DECREMENT":
      return state - 1;
    default:
      return state;
  }
}

function Counter() {
  const [number, dispatch] = useReducer(reducer, 0);

  const onIncrease = () => {
    dispatch({ type: "INCREMENT" });
  };

  const onDecrease = () => {
    dispatch({ type: "DECREMENT" });
  };

  return (
    <div>
      <h1>{number}</h1>
      <button onClick={onIncrease}>+1</button>
      <button onClick={onDecrease}>-1</button>
    </div>
  );
}

export default Counter;
function reducer(state, action) {
  switch (action.type) {
    case "CHANGE_INPUT":
      return {
        ...state,
        inputs: {
          ...state.inputs,
          [action.name]: action.value,
        },
      };
    default:
      return state;
  }
}
  • reducerํ•จ์ˆ˜์—์„œ ์ƒˆ๋กœ์šด ์ƒํƒœ ๋งŒ๋“ค ๋•Œ, ๋ถˆ๋ณ€์„ฑ ์ง€์ผœ์ฃผ์–ด์•ผ ํ•จspread ์—ฐ์‚ฐ์ž ์‚ฌ์šฉ

useReducer vs useState

→ ์ƒํ™ฉ์— ๋”ฐ๋ผ ๋‹ค๋ฆ„

ex)

  • ์ปดํฌ๋„ŒํŠธ์—์„œ ๊ด€๋ฆฌํ•˜๋Š” ๊ฐ’์ด ํ•˜๋‚˜์ด๊ณ , ๊ทธ ๊ฐ’์ด ๋‹จ์ˆœํ•œ ์ˆซ์ž ํ˜น์€ ๋ฌธ์ž์—ด, boolean๊ฐ’useState ๋กœ ๊ด€๋ฆฌํ•˜๋Š” ๊ฒƒ์ด ํŽธ๋ฆฌ
  • ์ปดํฌ๋„ŒํŠธ์—์„œ ๊ด€๋ฆฌํ•˜๋Š” ๊ฐ’์ด ์—ฌ๋Ÿฌ ๊ฐœ๊ฐ€ ๋˜์–ด์„œ ์ƒํƒœ์˜ ๊ตฌ์กฐ๊ฐ€ ๋ณต์žก useReducer๋กœ ๊ด€๋ฆฌ

'ํ”„๋ก ํŠธ์—”๋“œ > React' ์นดํ…Œ๊ณ ๋ฆฌ์˜ ๋‹ค๋ฅธ ๊ธ€

Context API  (0) 2022.11.24
์ปค์Šคํ…€ Hooks ๋งŒ๋“ค๊ธฐ  (0) 2022.11.24
useCallback, React.memo  (0) 2022.11.24
useEffect์™€ useMemo  (0) 2022.11.23
์ปดํฌ๋„ŒํŠธ ๋ Œ๋”๋ง  (0) 2022.11.23