javascript / intermediate
Snippet
Relational State Indexing with JavaScript Maps in React
When managing normalized or keyed data in React state, primitive JavaScript `Map` objects provide O(1) lookups and maintain insertion order. Because React state requires immutability, updating a Map involves cloning it into a new instance using `new Map(prevMap)` before setting updated values.
snippet.js
javascript
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
import { useState } from 'react';export function UserDirectory({ initialUsers }) {const [usersById, setUsersById] = useState(() =>new Map(initialUsers.map(user => [user.id, user])));const updateRole = (userId, newRole) => {setUsersById(prevMap => {const user = prevMap.get(userId);if (!user || user.role === newRole) return prevMap;const nextMap = new Map(prevMap);nextMap.set(userId, { ...user, role: newRole });return nextMap;});};const userList = Array.from(usersById.values());return (<ul>{userList.map(user => (<li key={user.id}>{user.name} ({user.role})<button onClick={() => updateRole(user.id, 'admin')}>Promote</button></li>))}</ul>);}
react
Breakdown
1
new Map(initialUsers.map(user => [user.id, user]))
Constructs a keyed Map from an array of entity objects using their unique identifiers as keys.
2
const nextMap = new Map(prevMap);
Creates a shallow clone of the Map instance to preserve state immutability in React.
3
const userList = Array.from(usersById.values());
Converts the Map values iterator back into a standard array to allow `.map()` rendering in JSX.