A state update function is a function passed to a state setter. React calls it with the current state, and its return value becomes the next state. Use a direct value when the replacement is fixed; use an update function when the next value depends on the current one. section 5.2.5
Choose the setter form that matches the update:
- Set a fixed value: setExpanded(false) or setCounter(0). section 5.2.5
- Derive a value from current state: setCounter((value) => value + 1). section 5.2.5
- For arrays, return a new array rather than mutating and resubmitting the existing one, so React can detect the update. section 5.2.5
- When storing a function as state, wrap it so the setter receives a function that returns the operator function. section 5.2.5
Removing a task
setTodos((value) => [ ...value.slice(0, index), ...value.slice(index + 1), ]); section 5.2.5
Listing 5.7 A proper to-do list application
import { useState } from "react";
function TodoApplication({ initialList }) {
const [todos, setTodos] = useState(initialList);
return (
<main>
{todos.map((todo, index) => (
<p key={todo}>
{todo}
<button
onClick={() => {
setTodos((value) => [ #1
...value.slice(0, index), #1
...value.slice(index + 1), #1
]);
}}
>
x
</button>
</p>
))}
</main>
);
}
function App() {
const items = ["Feed the plants", "Water the dishes", "Clean the cat"];
return <TodoApplication initialList={items} />;
}
export default App;
A complete to-do list demonstrates deriving the next array from the current state without mutation. section 5.2.5
