Problem

Write a function createCounter. It should accept an initial integer init. It should return an object with three functions.

The three functions are:

  • increment() increases the current value by 1 and then returns it.
  • decrement() reduces the current value by 1 and then returns it.
  • reset() sets the current value to init and then returns it.

Examples

Example 1

1
2
3
4
5
6
7
Input: init = 5, calls = ["increment","reset","decrement"]
Output: [6,5,4]
Explanation:
const counter = createCounter(5);
counter.increment(); // 6
counter.reset(); // 5
counter.decrement(); // 4

Example 2

1
2
3
4
5
6
7
8
9
Input: init = 0, calls = ["increment","increment","decrement","reset","reset"]
Output: [1,2,1,0,0]
Explanation:
const counter = createCounter(0);
counter.increment(); // 1
counter.increment(); // 2
counter.decrement(); // 1
counter.reset(); // 0
counter.reset(); // 0

Constraints

  • -1000 <= init <= 1000
  • 0 <= calls.length <= 1000
  • calls[i] is one of “increment”, “decrement” and “reset”

Solution

Method 1 – Closure with Object Methods

Intuition

The key idea is to use a closure to capture the current value and initial value. The returned object exposes three methods that manipulate and return the value as required, maintaining state between calls.

Approach

  1. Define a function createCounter that takes an integer init.
  2. Inside, define a variable to store the current value.
  3. Return an object with three methods:
    • increment: increases the value by 1 and returns it.
    • decrement: decreases the value by 1 and returns it.
    • reset: sets the value to init and returns it.
  4. The closure ensures the value persists across calls.

Code

1
2
3
4
5
6
7
8
function createCounter(init) {
    let val = init;
    return {
        increment: () => ++val,
        decrement: () => --val,
        reset: () => (val = init)
    };
}
1
2
3
4
5
6
7
8
function createCounter(init: number): { increment: () => number; decrement: () => number; reset: () => number } {
    let val = init;
    return {
        increment: (): number => ++val,
        decrement: (): number => --val,
        reset: (): number => (val = init)
    };
}

Complexity

  • ⏰ Time complexity: O(1), each call returns and updates a number in constant time.
  • 🧺 Space complexity: O(1), only a single variable is stored in the closure.