Let’s say you’re building a dashboard that filters a list of users based on a search term. Without useMemo, the filtering logic might run on every render, even if the data or search term hasn’t changed.
Here’s how you might implement this without useMemo:
import React, { useState } from ‘react’;
function UserList({ users }) {
const [searchTerm, setSearchTerm] = useState(”);
const filteredUsers = users.filter(user =>
user.name.toLowerCase().includes(searchTerm.toLowerCase())
);
return (
<div>
<input
value={searchTerm}
onChange={e => setSearchTerm(e.target.value)}
placeholder=”Search users…”
/>
<ul>
{filteredUsers.map(user => (
<li key={user.id}>{user.name}</li>
))}
</ul>
</div>
);
}
export default UserList;
In this example, filteredUsers recalculates every time the component renders, even if users or searchTerm hasn’t changed. For a small list, this might not be noticeable, but with thousands of users, it could lead to laggy performance.
Now, let’s optimize it with useMemo:
import React, { useState, useMemo } from ‘react’;
function UserList({ users }) {
const [searchTerm, setSearchTerm] = useState(”);
const filteredUsers = useMemo(() => {
return users.filter(user =>
user.name.toLowerCase().includes(searchTerm.toLowerCase())
);
}, [users, searchTerm]);
return (
<div>
<input
value={searchTerm}
onChange={e => setSearchTerm(e.target.value)}
placeholder=”Search users…”
/>
<ul>
{filteredUsers.map(user => (
<li key={user.id}>{user.name}</li>
))}
</ul>
</div>
);
}
export default UserList;
- With useMemo, the filtering only happens when users or searchTerm changes. This small change can make a big difference in performance.