Cover image

React: Avoid Unnecessary Renders with Batch State Updates

February 10, 2022

6 min read

Introduction

Copy heading link

Have you ever wondered why your component is re-rendering multiple times consecutively when you only expect it to re-render once? Perhaps you update some local state and somehow multiple renders occur as a result? Let's take this hooks-based example:

JSX
image-ce2269b483ba50dfc5247c5225435a1e5bab055a-640x480-gif

Under synchronous operations or with React event handlers, React will batch all setState calls into a single render. However, React does not batch setState calls when performing asynchronous operations. There are three solutions that I propose to clean up the unnecessary re-renders.

Solution A: Combine state

Copy heading link

This solution couples dateA and dateB into a single object. This means that anytime you need to update dateA or dateB, you will be updating one object. The downside to this approach is that dateA and dateB will always be tightly coupled and you will always need to know the previous state to merge in with the new state when updating just one of the two dates.

JSX

Solution B: Batch update API

Copy heading link

This solution involves using React’s unstable_batchedUpdates API. Although labelled unstable, I have not experienced any issues with this method. React does plan on implementing this behaviour as the default behaviour soon. This is probably the cleanest solution that decouples dateA and dateB.

JSX

Solution C: useReducer hook

Copy heading link

useReducer implements a redux state pattern into your local state. This allows you to perform multiple state updates in a single dispatch call. The redux state pattern is highly reliable but does require a lot of boilerplate code to write a reducer and your dispatch calls. If you’re using TypeScript, this adds a lot of bloat to a single component.

JSX

Bonus: Batching Redux dispatch calls

Copy heading link

Another cause of excessive renders could come from your global state. Redux uses the unstable_batchedUpdates API under the hood to batch their dispatch actions into a single call. This batch behaviour can be confirmed using the Redux Dev Tools.

JSX

Full demo of all 3 solutions are available on Code Sandbox.

Newsletter