React useReducer

정현승·2024년 12월 2일

useReducer

useReducer는 상태 관리를 위한 React Hook입니다.
상태와 업데이트 로직이 복잡하거나 여러 동작을 처리해야 할 때, useReducer는 더 구조적인 방식을 제공합니다.

function reducer(state, action) {
  switch (action.type) {
    case "ACTION_TYPE_1":
      return { ...state, key: newValue }; // 새로운 상태 반환
    case "ACTION_TYPE_2":
      return { ...state, key: anotherValue };
    default:
      return state; // 기본 상태 반환
  }
}


const [state, dispatch] = useReducer(reducer, initialState);
  • 상태(state): 현재 상태 값.
  • 리듀서(reducer): 상태를 업데이트하는 함수. 리듀서는 항상 값을 반환해야 합니다. 각 리듀서는 독립적으로 관리합니다.
  • 액션(action): 상태 변경을 지시하는 객체.
  • initialState: 초기 값.
  • dispatch: 액션을 리듀서에 전달하는 함수.

카운터 예제

import React, { useReducer } from "react";

const initialState = { count: 0 };

function reducer(state, action) {
  switch (action.type) {
    case "increment":
      return { count: state.count + 1 };
    case "decrement":
      return { count: state.count - 1 };
    case "reset":
      return { count: 0 };
    default:
      throw new Error("Unhandled action type");
  }
}

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

  return (
    <div>
      <p>Count: {state.count}</p>
      <button onClick={() => dispatch({ type: "increment" })}>+</button>
      <button onClick={() => dispatch({ type: "decrement" })}>-</button>
      <button onClick={() => dispatch({ type: "reset" })}>Reset</button>
    </div>
  );
}

export default Counter;

복잡한 상태 관리

useReducer는 상태가 다중 필드로 구성되어 있거나, 여러 동작을 처리해야 할 때 유용합니다.

import React, { useReducer } from "react";

const initialState = {
  username: "",
  email: "",
  password: "",
};

function reducer(state, action) {
  switch (action.type) {
    case "update_field":
      return { ...state, [action.field]: action.value };
    case "reset":
      return initialState;
    default:
      throw new Error("Unhandled action type");
  }
}

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

  const handleChange = (e) => {
    dispatch({
      type: "update_field",
      field: e.target.name,
      value: e.target.value,
    });
  };

  return (
    <form>
      <input
        name="username"
        value={state.username}
        onChange={handleChange}
        placeholder="Username"
      />
      <input
        name="email"
        value={state.email}
        onChange={handleChange}
        placeholder="Email"
      />
      <input
        name="password"
        type="password"
        value={state.password}
        onChange={handleChange}
        placeholder="Password"
      />
      <button type="button" onClick={() => dispatch({ type: "reset" })}>
        Reset
      </button>
    </form>
  );
}

export default Form;

useState vs useReducer

특징useStateuseReducer
복잡성간단한 상태 관리복잡한 상태 관리에 적합
상태 구조단일 값 또는 간단한 객체다수의 값 또는 복잡한 객체
업데이트 로직로직은 컴포넌트 내부에 직접 구현리듀서 함수로 외부화하여 관리
액션 방식업데이트 함수 호출 (값 또는 함수로)명시적 액션 객체를 사용
사용 사례폼 입력, 토글 상태, 간단한 카운터 등폼 상태 관리, 복잡한 UI 상태, API 데이터 관리 등

0개의 댓글