Skip to main content

useReducer vs useState

What useReducer does

useReducer is a React hook that lets you manage state through a reducer function. It works like Redux:

state is not changed directly, but through an "action".


Syntax

javascript
const [state, dispatch] = useReducer(reducer, initialState);
  • state is the current state
  • dispatch is a function that dispatches an "action"
  • reducer(state, action) is a function that receives the current state and an "action" and returns the new state

Simple example

javascript
function reducer(state, action) { switch (action.type) { case "increment": return { count: state.count + 1 }; case "decrement": return { count: state.count - 1 }; default: return state; } } function Counter() { const [state, dispatch] = useReducer(reducer, { count: 0 }); return ( <div> <p>{state.count}</p> <button onClick={() => dispatch({ type: "increment" })}>+</button> <button onClick={() => dispatch({ type: "decrement" })}>-</button> </div> ); }

How it works:

  1. On click, React calls dispatch({ type: "increment" }).
  2. React calls reducer(state, action).
  3. The reducer returns a new state -> React re-renders the component.

How useReducer differs from useState

CriterionuseStateuseReducer
State typeSimple (single value)Complex (object, array, update logic)
UpdatesetState(newValue)dispatch({ type, payload })
Update logicDirectly in the componentMoved into a separate function (reducer)
When to useSimple cases (counter, form, toggle)When state is complex or driven by different actions
Good fit forSmall componentsLarge / complex state
Similar toA built-in Redux alternativeA mini-Redux inside a single component

Comparison example

Version with useState

javascript
const [count, setCount] = useState(0); const increment = () => setCount(count + 1); const decrement = () => setCount(count - 1);

Simple, but does not scale well when the logic gets complex.


Version with useReducer

javascript
function reducer(state, action) { switch (action.type) { case "increment": return { ...state, count: state.count + 1 }; case "decrement": return { ...state, count: state.count - 1 }; case "reset": return { ...state, count: 0 }; default: return state; } } const [state, dispatch] = useReducer(reducer, { count: 0 });

Now you can manage the logic centrally, which is convenient when there are many branches or states.


When it's better to use useReducer

Use useReducer when:

  1. The state is complex (for example, an object with several fields).
  2. Update logic depends on different action types.
  3. Multiple parts of the code can update the same state.
  4. You want to separate the logic (reducer) from the UI component.

Examples:

  • A form with validation
  • A multi-step process (wizard / onboarding)
  • A list of items with filtering, sorting, adding, removing

A "form" example with useReducer

javascript
function formReducer(state, action) { switch (action.type) { case "changeField": return { ...state, [action.field]: action.value }; case "reset": return { name: "", email: "" }; default: return state; } } function Form() { const [form, dispatch] = useReducer(formReducer, { name: "", email: "" }); return ( <form> <input value={form.name} onChange={(e) => dispatch({ type: "changeField", field: "name", value: e.target.value }) } /> <input value={form.email} onChange={(e) => dispatch({ type: "changeField", field: "email", value: e.target.value }) } /> <button onClick={() => dispatch({ type: "reset" })}>Clear</button> </form> ); }

Now you can easily extend the form, just add a new case.


Summary

QuestionAnswer
What does useReducer do?Manages state through a reducer function, reacting to "actions"
How does it differ from useState?useState just stores a value, useReducer manages complex logic
When to use it?For complex or related updates
When not to?For simple numbers, strings, flags - useState is simpler
How is it similar to Redux?The same "action -> reducer -> new state" principle, just local

Short Answer

Interview ready
Premium

A concise answer to help you respond confidently on this topic during an interview.