Search code examples
javascriptstack

Counting values of a stack using a javascript algorithm


I need help figuring out how to make a JavaScript algorithm that count the values of a stack, I am given 3 custom methods

stack - a Stack object containing zero or more values.

.pop() which pops the top value of the stack

.push() which pushes a value on to the stack

.peek() which shows me the top value of the stack without modifying the stack

I tried simply returning the length of said stack like so

function countValues(stack) {
  return stack.length
}

but i get back undefined thus having no success

this is the stack class that was used to implement the custom methods

class Stack {

  constructor(...values) {

    const data = {};

    let index = 0;

    this.push = function (value) {
      if (arguments.length < 1) {
        throw new TypeError('stack.push() requires a value argument');
      }
      if (typeof value === 'undefined') {
        throw new TypeError('stack.push(value) received undefined');
      }
      data[index] = value;
      index++;
    };

    this.pop = function () {
      const last = index - 1;
      if (last < 0) return;
      const value = data[last];
      delete data[last];
      index = last;
      return value;
    };

    this.peek = function () {
      const last = index - 1;
      if (last < 0) return;
      return data[last];
    };

    this.print = function () {
      if (index === 0) {
        return 'Stack { <empty> }';
      }
      let output = ' }';
      let last = index - 1;
      for (; last > 0; last--) {
        output = ' <- ' + JSON.stringify(data[last]) + output;
      }
      output = JSON.stringify(data[last]) + output;
      return 'Stack { ' + output;
    };

    for (let i = 0; i < values.length; i++) {
      this.push(values[i]);
    }

    Object.freeze(this);

  }

}


Solution

  • class Stack {
      constructor(...values) {
    
        const data = {};
    
        let index = 0;
    
        this.push = function(value) {
          if (arguments.length < 1) {
            throw new TypeError('stack.push() requires a value argument');
          }
          if (typeof value === 'undefined') {
            throw new TypeError('stack.push(value) received undefined');
          }
          data[index] = value;
          index++;
        };
    
        this.pop = function() {
          const last = index - 1;
          if (last < 0) return;
          const value = data[last];
          delete data[last];
          index = last;
          return value;
        };
    
        this.peek = function() {
          const last = index - 1;
          if (last < 0) return;
          return data[last];
        };
    
        this.print = function() {
          if (index === 0) {
            return 'Stack { <empty> }';
          }
          let output = ' }';
          let last = index - 1;
          for (; last > 0; last--) {
            output = ' <- ' + JSON.stringify(data[last]) + output;
          }
          output = JSON.stringify(data[last]) + output;
          return 'Stack { ' + output;
        };
    
        for (let i = 0; i < values.length; i++) {
          this.push(values[i]);
        }
    
        Object.freeze(this);
      }
    }
    
    const myStack = new Stack(1, 2, 3, 4, 5);
    
    // Here's an easy but not so good way:
    function countValues1(stack) {
      return Array.from(stack.print()).filter(x => x === "<").length + 1;
    }
    
    // Here's another way, but it mutates the stack:
    function countValues2(stack) {
      let count = 0;
      while (true) {
        if (stack.pop() === undefined) {
          break;
        }
        count++;
      }
      
      return count;
    }
    
    console.log(countValues1(myStack));
    console.log(countValues2(myStack));

    Without knowing exactly how stack works, or specifically what you need (are you allowed to modify the stack implementation? are you allowed to mutate the contents of the stack?) we'll struggle for a good answer, but the above should help get you maybe slightly closer perhaps.