Imperative programming describes computation as a detailed sequence of top-to-bottom statements. Each statement can change the program’s state, so the code specifies both the task and the steps for performing it. section 1.2
Squaring an array with mutation
A loop visits each element and replaces it with its square: `var array = [0, 1, 2, 3]; for (let i = 0; i < array.length; i++) { array[i] = Math.pow(array[i], 2); }` The loop, index, order, and assignment are all explicit. section 1.2
State changes become difficult to reason about when functions read or modify shared data. A global counter makes repeated calls depend on what happened before, limiting isolation and making tests inconsistent. section 6.2
Common consequences of stateful imperative design include:
- Monolithic functions can combine validation, data retrieval, error handling, and DOM updates, making their units of modularity hard to identify. section 6.2
- Shared resources can make test results depend on execution order rather than on each test’s own inputs. section 6.2
- Functional rewrites reduce direct state changes by expressing transformations with operations such as `map` and by separating business steps into composable functions. section 1.2













