Create a Priority Queue Class

Tell us what’s happening:
Hi guys! Soo I wrote some code for the Priority Queue challenge and after I run it I’m getting green light for all the requirements except:
Your Queue class should have a dequeue method.
Your Queue class should have a size method.
Your Queue class should have an isEmpty method.
and I don’t get it, because evidently I have those methods in my class.
thx in advance and sorry for my bad english

Your code so far


function PriorityQueue () {
    this.collection = [];
    this.printCollection = function() {
      console.log(this.collection);
    };
    // Only change code below this line
    this.enqueue=function(item){
        if(this.collection.length===0) {
        this.collection.push(item);
      }
      else if(this.collection.length===1){
        if(item[1]>=this.collection[0][1]){
          this.collection.push(item);
        }
        else if(item[1]<this.collection[0][1]){
          this.collection.unshift(item);
        }
      }
     else if(this.collection.length>1){
        var check=false;
        for(let i=0;i<this.collection.length;i++){
            if(this.collection[i][1]>item[1]){
              if(i===0){
                check=true;
                this.collection.unshift(item);
                break;
              }
              else {
                check=true;
                var sliced=this.collection.slice(0,i);
                var slicedend=this.collection.slice(i,this.collection.length);
                sliced.push(item);
                this.collection=sliced.concat(slicedend);
                break;
              }
            }
        }
        if(!check){
                this.collection.push(item);
        }
    };


    this.dequeue = function(){
        return this.collection.shift()[0];
    };
    this.size = function(){
        return this.collection.length;
    };
    this.isEmpty=function(){
        return this.collection.length===0?true:false;
    };
    this.front=function(){
        return this.collection[0];
    };
    }
    // Only change code above this line
}

Your browser information:

User Agent is: Mozilla/5.0 (Windows NT 6.3; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/66.0.3359.181 Safari/537.36.

Link to the challenge:
https://learn.freecodecamp.org/coding-interview-prep/data-structures/create-a-priority-queue-class

You’re missing a closing bracket somewhere around here:

    if(!check){
                this.collection.push(item);
        }
};

And there’s an extra bracket here, which means the brackets match, but are in the wrong place (everything is inside the enqueue function):

    this.front=function(){
        return this.collection[0];
    };
    }
    // Only change code above this line
}

Your enqueue function is incredibly complex: for a start, if you’ve got more than two levels of nesting you really need to refactor, it’s very difficult to keep track of things.

oh yeah, silly me.
also i’ll try to write simpler and cleaner code in the future. thx again

Your dequeue method it is such an overkill.
here is a suggestion for refactoring

   enqueue(item){
            let element = item[0], priority = item[1], check = false;

          for(let i = 0; i < this.collection.length; i++){
            if(this.collection[i][1] > priority){
                this.collection.splice(i,0,item);
                check = true;
                break;
            } 
          }
          if(!check)
              this.collection.push(item);
      }

1 Like

Continuing the discussion from Create a Priority Queue Class:

function PriorityQueue () {
    this.collection = [];
    this.printCollection = function() {
      console.log(this.collection);
    };
    // Only change code below this line

    this.enqueue = function(priorityItem){
        let inserted = false;
        for(let i=0; i<this.collection.length; i++){
            let _value = this.collection[i];
            if(_value[1] > priorityItem[1]){
                this.collection.splice(i, 0, priorityItem);
                inserted = true;
                break;
            }
        }

        if(!inserted){
            this.collection.push(priorityItem);
        }
    }
    this.dequeue = function(){
        return this.collection.shift();
    }
    this.size = function(){
        return this.collection.length;
    }
    this.isEmpty = function(){
        return this.collection.length === 0;
    }
    this.front = function(){
        return this.collection[0];
    }
    // Only change code above this line
}

What is wrong with my above implementation? All the test cases have been passed except,

The priority queue should return items with a higher priority before items with a lower priority and return items in first-in-first-out order otherwise.

Kindly check and revert. Thanks in advance.

The task being “push” ed at the end is implicitly becoming low priority. how about using unshift() to add a new task so it becomes high priority ?

I don’t know how it will be the solution George. Even changing push to unshift didn’t work.

Solution found.

It was said in the question that,

The dequeue should return only the current item, not its priority.

So, changing deque function like below gives the solution.

this.dequeue = function(){
        let val = this.collection.shift();
        return val[0];
 }

Thanks for the help.

2 Likes

In this function does the let inserted=false; variable get converted back to false after break; is run?

If so, how? Wouldn’t running let inserted=false; again throw an error because let inserted; has already been declared?

If not, wouldn’t this function not properly work because there is no code setting it back to false. Right?

My overall question is, if inserted does get redefined to true, how does inserted get set back to false? Or does it stay true forever? Thanks.

this.enqueue = function(priorityItem){
        let inserted = false;
        for(let i=0; i<this.collection.length; i++){
            let _value = this.collection[i];
            if(_value[1] > priorityItem[1]){
                this.collection.splice(i, 0, priorityItem);
                inserted = true;
                break;
            }
        }

        if(!inserted){
            this.collection.push(priorityItem);
        }
    }

You probably already have this answer by now. But in case you still haven’t, maybe I can help.

If the ‘inserted’ is converted to ‘true’, it means that the ‘if’ statement was true. When that happens, the ‘break’ command stops the ‘for’ loop from incrementing ‘i’ and prevents loop from continuing.

So, once the ‘inserted’ value has been converted from ‘false’ to ‘true’, it is never converted back to ‘false’ because the loop has stopped.

If the ‘if’ statement did not run (the condition(s) were not met), then the value of the ‘inserted’ would still be ‘false’. The second ‘if’ statement passes and runs the command in it.

So, basically, the value if ‘inserted’ only changes once or does not change at all.
:slight_smile:

Hello!
I want to show my decision for this exersize.
I got green light too) it’s really great!
Code is short but it may take more time for complete if array is big.

function PriorityQueue () {
    this.collection = [];
    this.elem;
    this.printCollection = function() {
      console.log(this.collection);
    };
    // Only change code below this line

    this.enqueue = function(elem) {
      let buffer;
      let priorityClass = elem[1];
      this.collection.forEach(function(element, index) {
        if (priorityClass >= element[1])  buffer = index + 1;
      })
      this.collection.splice(buffer, 0, elem);
      // this._elem++;
    }

    this.dequeue = function() {
        if(this.collection.length - this._first === 0) return console.log("Array is empty");

        return this.collection.shift()[0];
    }

    this.size = function() {
      return this.collection.length;
    }

    this.isEmpty = function() {
      return this.collection.length === 0;
    }

    // Only change code above this line
}

This helped a lot! Finally I got it to pass!