Skip to main content

`React.memo` for Component Memoization (Part 2): A Practical Example #123

📖 Introduction

Following our introduction to React.memo, this article provides a practical, hands-on example of how to use it to prevent unnecessary re-renders. We will also explore how to use a custom comparison function to handle more complex props.


📚 Prerequisites

Before we begin, please ensure you have a solid grasp of the following concepts:

  • All concepts from Part 1 of this series.
  • JavaScript objects and reference equality.

🎯 Article Outline: What You'll Master

In this article, you will learn:

  • The Problem with Object Props: Understanding why React.memo's default shallow comparison can fail with object props.
  • Custom Comparison Functions: How to provide a custom comparison function to React.memo to handle complex props.
  • Practical Application: Building a simple application that demonstrates the use of React.memo with a custom comparison function.

🧠 Section 1: The Core Concepts of React.memo with Complex Props

React.memo works by doing a shallow comparison of a component's props. This works great for primitive values like strings and numbers, but it can be problematic when dealing with objects and arrays.

This is because in JavaScript, objects and arrays are reference types. This means that even if two objects have the same properties and values, they are not considered equal if they are not the same object in memory.

When a parent component re-renders, it will often create new objects and arrays, even if the data they contain is the same. This will cause a child component wrapped in React.memo to re-render, because the prop references have changed.

To solve this, we can provide a custom comparison function as the second argument to React.memo. This function gives us full control over the prop comparison logic.


💻 Section 2: Deep Dive - Implementation and Walkthrough

Let's build a simple application to demonstrate this.

2.1 - The UserProfile Component

First, let's create a UserProfile component that takes a user object as a prop.

// UserProfile.js
import React from 'react';

const UserProfile = ({ user }) => {
console.log('UserProfile re-rendered');
return (
<div>
<h2>{user.name}</h2>
<p>Age: {user.age}</p>
</div>
);
};

export default React.memo(UserProfile);

2.2 - The App Component

Now, let's create an App component that renders the UserProfile component.

// App.js
import React, { useState } from 'react';
import UserProfile from './UserProfile';

function App() {
const [count, setCount] = useState(0);

const user = {
name: 'John Doe',
age: 30,
};

return (
<div>
<p>Parent count: {count}</p>
<button onClick={() => setCount(count + 1)}>Increment Parent</button>
<UserProfile user={user} />
</div>
);
}

export default App;

If you run this code, you will see that the UserProfile component re-renders every time the "Increment Parent" button is clicked. This is because a new user object is created on every render of the App component.

2.3 - The Custom Comparison Function

Now, let's add a custom comparison function to our UserProfile component.

// UserProfile.js
import React from 'react';

const UserProfile = ({ user }) => {
console.log('UserProfile re-rendered');
return (
<div>
<h2>{user.name}</h2>
<p>Age: {user.age}</p>
</div>
);
};

function areEqual(prevProps, nextProps) {
return prevProps.user.name === nextProps.user.name &&
prevProps.user.age === nextProps.user.age;
}

export default React.memo(UserProfile, areEqual);

Now, the UserProfile component will only re-render if the name or age properties of the user object change.


💡 Conclusion & Key Takeaways

In this article, we've learned how to use a custom comparison function with React.memo to prevent unnecessary re-renders of components with complex props. This is a powerful technique for optimizing the performance of your React applications.

Let's summarize the key takeaways:

  • React.memo's default shallow comparison can fail with object and array props.
  • You can provide a custom comparison function to React.memo to handle complex props.
  • The custom comparison function should return true if the props are equal and the component should not re-render.

Challenge Yourself: To solidify your understanding, try to create a component that takes an array of items as a prop and use a custom comparison function to prevent it from re-rendering if the items in the array have not changed.


➡️ Next Steps

You now have a solid understanding of how to use React.memo with a custom comparison function. In the next article, "useMemo for Memoizing Expensive Calculations (Part 1)", we will explore another powerful tool for optimizing performance: the useMemo hook.

Thank you for your dedication. Stay curious, and happy coding!


glossary

  • Reference Equality: Two objects are reference-equal if they are the same object in memory.
  • Custom Comparison Function: A function that you provide to React.memo to control the prop comparison logic.

Further Reading