HuntExams Academy logo
ReactAdvanced#performance

What is React.memo?

Answer

A higher-order component that skips re-rendering a component when its props are shallowly equal to the previous props. It helps only when the component is expensive and its props are stable.

Example

const Row = React.memo(function Row({ item }) {
  return <li>{item.name}</li>;
});

Detailed explanation

React.memo is a higher-order component that returns a memoised version of a React component. It lets React skip rendering that component when its parent renders again but its props have not changed. For example, const Row = React.memo(function Row({ item }) { return <li>{item.name}</li>; }); creates a memoised Row. If the parent passes the same item reference on its next render, React can reuse the previous rendering work. This is a performance optimisation, not a guarantee that the component will never render again.

By default, React compares each new prop with its previous value using Object.is. This is commonly described as shallow comparison: primitive values are compared by value, while objects, arrays, and functions are compared by reference. If a parent creates item={{ name: 'Asha' }} during every render, that object has a new reference each time, so memo cannot skip the render based on default comparison. React does not recursively inspect item.name. Preserving references through appropriate state design, useMemo, or useCallback can make memoisation effective, but those tools should not be added automatically.

React.memo only addresses renders caused by receiving unchanged props from a parent. A memoised component still renders when its own state changes or when a context value it consumes changes. React also allows a custom comparison function as the second argument: memo(Component, arePropsEqual). Returning true means the props are equivalent for rendering and behaviour, so React may skip rendering. The comparison must account for every relevant prop, including callbacks, because ignoring a changed function can leave the component using a stale closure.

In interviews, explain the cost-benefit trade-off rather than presenting memo as a universal fix. Comparing props has a cost, and unstable props can eliminate the benefit. Memo is most useful when a component renders frequently with unchanged props and its rendering work is substantial; many small repeated components can also benefit collectively. Use React DevTools Profiler to validate an improvement. Modern React Compiler-enabled projects may receive equivalent automatic memoisation, reducing the need for manual React.memo.

Key points to remember

  • React.memo returns a memoised component that can skip parent-triggered renders when props are unchanged.
  • The default comparison uses Object.is for each prop, not deep equality.
  • New object, array, or function references can defeat default memoisation.
  • Local state changes and consumed context updates can still trigger rendering.
  • A custom comparator returns true to skip rendering; measure whether comparison is cheaper than rendering.

Common mistakes candidates make

  • Wrapping every component in memo without profiling or checking whether its props remain stable.
  • Expecting memo to detect nested object changes after mutating an object in place.
  • Ignoring callback props in a custom comparator, which can preserve stale closures and incorrect behaviour.

Likely follow-up questions

How is React.memo different from useMemo?

React.memo memoises a component boundary to potentially skip rendering when props are unchanged. useMemo caches a calculation result between renders until its dependencies change; it does not itself prevent the component from rendering.

Why does a memoised child still render when I pass a callback?

A function declared inside the parent is usually recreated on each render, so its reference changes. useCallback can stabilise that reference while its dependencies remain unchanged, if doing so provides a measurable benefit.

Can React.memo prevent renders caused by context updates?

No, a component consuming context can render when that context value changes even if its props are unchanged. You can separate the context-reading wrapper from an expensive memoised child and pass only the values that child needs.

Interview tip: Start with the definition, explain the item-reference example, and finish with the state/context limitation and profiling trade-off.

Related Interview Questions

1
ReactIntermediate#hooks#context

What is useContext and when do you use it?

Open
2
ReactAdvanced#hooks#state

When should you use useReducer instead of useState?

Open
3
ReactIntermediate#hooks

How do you create a custom hook?

Open