Closure in JavaScript
change url and proper title
A closure is a function that has access to variables in its outer (enclosing) lexical scope, even after the outer function has returned. Closures are created every time a function is created.
function outerFn() {
const test = 'test';
return function innerFn(){
return test;
}
}
const fn = outerFn();
console.log(fn());Counter Factory
function createCounter(start = 0, step = 1) {
let count = start;
let history = [];
let paused = false;
// Private helper - only accessible via closure
function validateNumber(value) {
if (typeof value !== 'number' || isNaN(value)) {
throw new Error('Must be a valid number');
}
}
return {
increment() {
if (paused) return count;
count += step;
history.push({ action: 'increment', value: count });
return count;
},
decrement() {
if (paused) return count;
count -= step;
history.push({ action: 'decrement', value: count });
return count;
},
setValue(value) {
validateNumber(value);
const oldCount = count;
count = value;
history.push({ action: 'set', from: oldCount, to: count });
return count;
},
getValue() {
return count;
},
pause() {
paused = true;
},
resume() {
paused = false;
},
reset() {
count = start;
history = [];
},
// Returns a new function that closes over current state
createSnapshot() {
const snapshot = count;
const snapshotHistory = [...history];
return {
restore() {
count = snapshot;
history = snapshotHistory;
},
getValue() {
return snapshot;
}
};
}
};
}
// Usage
const counter = createCounter(0, 2);
counter.increment(); // 2
counter.increment(); // 4
const snapshot = counter.createSnapshot();
counter.increment(); // 6
counter.increment(); // 8
snapshot.restore();
console.log(counter.getValue()); // 4 (restored)Why these are complex:
Multiple scope layers: Functions close over functions closing over variables
Private state management: No way to access variables except through returned methods
Memory persistence: State survives between function calls
Method chaining:
thiscontext within closuresClosure factories: Functions returning functions with captured state
Event loops and timers: Closures executing asynchronously while maintaining scope
Data structures: Maps, Sets, and arrays maintained across closures
Circular references: Methods referencing each other through closures
React example
function Counter() {
const [count, setCount] = useState(0);
const increment = () => {
setCount(count + 1); // Closure over 'count'
};
return <button onClick={increment}>{count}</button>;
}