0% found this document useful (0 votes)
13 views25 pages

Queue Implementation

Queue

Uploaded by

salmamoahmmed4
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
13 views25 pages

Queue Implementation

Queue

Uploaded by

salmamoahmmed4
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 25

Queue

1
Queue
A queue is a linear data structure that follows the FIFO (First-In-First-Out) principle, meaning that the element that is
inserted first is also the first one to be removed. It is an ordered list of homogeneous elements, where the insertions
take place at one end, called the "back or rear" and the deletions take place at the other end, called the "front."

The fundamental operations of a queue are:


 Enqueue: add an item to the back or rear of the queue.
 Dequeue: remove an item from the front of the queue.
 Size: get the number of items currently in the queue.
 Retrieve: get an item at the front of the queue without removing it.
 IsEmpty: check if the queue is empty.
 IsFull: check if the queue is full.

There are many queues applications CPU scheduling, shared resource management, simulation, breadth-first search,
network congestion control, etc.

The queue can be implemented using an array or using a linked list.

2
Stack (implementation)

Please write the implementation in the following files


 Queue.h
 Queue.cpp
 main.cpp

3
Queue (linked-based implementation)

4
Queue (linked-based implementation)
#include <iostream> /* Function to check if the queue is
using namespace std; empty*/
template<class T> bool isEmpty();
class Node { /* Function to add an element to the
public: back of the queue*/
T data; /* Data stored in the node*/ void enqueue(T item);
Node<T>* next; /* Pointer to the next node in the list*/ /* Function to remove the front element
}; from the queue*/
/* Queue class using a linked list*/ void dequeue(T& item);
template<class T> /* Function to retrieve the front
class Queue { element from the queue*/
private: void retrieve(T& item);
Node<T>* front; /* Pointer to the front node of the /* Function to display all elements in
queue*/ the queue*/
Node<T>* back; /* Pointer to the back node of the queue*/ void display();
int size; /* Size of the queue */ /* Function to return the size of
public: the queue */
/* Constructor to initialize an empty queue*/ int getSize();
Queue(); };
/* Destructor to deallocate memory*/
~Queue();

5
Queue (linked-based implementation)
/* Constructor to initialize an empty queue*/ /* Function to add an element to the back of the
template<class T> queue*/
Queue<T>::Queue() { template<class T>
front = NULL; /* Set the front pointer to void Queue<T>::enqueue(T item) {
NULL*/ /* Create a new node with the given data*/
back = NULL; /* Set the back pointer to NULL*/ Node<T>* newNode = new Node<T>;
size = 0; /* Set the size of the queue to newNode->data = item;
0*/ newNode->next = NULL;
}
/* If the queue is empty, the new node becomes
/* Destructor to deallocate memory*/ both the front and back node*/
template<class T> if (front==NULL) {
Queue<T>::~Queue() { front = newNode;
/* Deallocate memory for all nodes in the queue*/ back = newNode;
while (front != NULL) { }
Node<T>* temp = front; /* Otherwise, add the new node to the back of
front = front->next; the queue*/
delete temp; else {
} back->next = newNode;
back = NULL; back = newNode;
size = 0; /* Reset the size of the queue to }
0*/ /* Increase the size of the queue*/
} size++; } 6
Queue (linked-based implementation)
/* Function to remove the front element from the /* Function to check if the queue is empty*/
queue*/ template<class T>
template<class T> bool Queue<T>::isEmpty() {
void Queue<T>::dequeue(T& item) { return size==0; /* If front== NULL or or
/* Check if the queue is empty*/ size == 0 or front==NULL*/
if (front==NULL) { }
cout << "Queue is empty" << endl; /* Function to retrieve the front element from
} the queue*/
else { template<class T>
/* Remove the front node and set the front void Queue<T>::retrieve(T& item) {
pointer to the next node*/ /* Check if the queue is empty*/
Node<T>* temp = front; if (isEmpty()) {
front = front->next; cout << "Queue is empty" << endl;
item = front->data; /* Retrieve the data }
from the front node*/ else
delete temp; item= front->data;
}
/* If the queue becomes empty, set the back
pointer to NULL*/
if (front==NULL)
back = NULL;
/* Decrease the size of the queue*/
size--;
}} 7
Queue (linked-based implementation)
/* Function to display all elements in the queue*/
template<class ItemType>
void Queue<ItemType>::display() {
if (front==NULL) {
cout << "Queue is empty" << endl;
} else {
Node<ItemType>* temp = front;
while (temp != NULL) {
cout << temp->data << " ";
temp = temp->next;
}
cout << endl;
}
}

/* Function to return the size of the queue */


template<class T>
int Queue<T>::getSize() {
return size;
}

8
Queue (array-based implementation)
(fixed-size array)

9
Queue (array-based implementation)

#include <iostream>
using namespace std;

#define MAX_SIZE 100 // Maximum size of the queue

template <class T>


class Queue {
private:
int front, back; // Indices of the front and back of the queue
T arr[MAX_SIZE]; // Array to store the elements of the queue
int size; // Number of elements in the queue
public:
Queue(); // Constructor to initialize the front, back, and size variables
bool isEmpty(); // Function to check if the queue is empty
bool isFull(); // Function to check if the queue is full
void enqueue(T item); // Function to insert an element at the back of the queue
void dequeue(T& item); // Function to remove an element from the front of the queue
void retrieve(T& item); // Function to return the element at the front of the queue
void display(); // Function to display the elements of the queue
int getSize(); /* Function to return the size of the queue */
};
10
Queue (array-based implementation)
template <class T> template <class T>
Queue<T>::Queue() { bool Queue<T>::isFull() {
front = -1; return (size == MAX_SIZE);
back = -1; }
size = 0;
} template <class T>
void Queue<T>::dequeue(T& item) {
template <class T> if (isEmpty()) {
bool Queue<T>::isEmpty() { cout << "Error: Queue is empty" << endl;
return (size == 0); return;
} }
template <class T> else if (front == back) {
void Queue<T>::enqueue(T item) { item = arr[front];
if (isFull()) { front = back = -1;
cout << "Error: Queue is full" << endl; }
return; } else {
else if (isEmpty()) { item = arr[front];
front = back = 0; } front = (front + 1) % MAX_SIZE;
else { }
back = (back + 1) % MAX_SIZE; } size--;
arr[back] = item; }
size++;
} 11
Queue (array-based implementation)
template <class T>
void Queue<T>::retrieve(T& item) {
if (isEmpty()) {
cout << "Error: Queue is empty" << endl;
return;
}
item = arr[front];
}

template <class T>


void Queue<T>::display() {
if (isEmpty()) {
cout << "Queue is empty" << endl;
return;
}
int i = front;
while (i != back) {
cout << arr[i] << " ";
i = (i + 1) % MAX_SIZE;
}
cout << arr[back] << endl;
}
12
Queue (array-based implementation) (dynamic array)

13
Queue (array-based implementation) (dynamic-array)
#include <iostream> template <class T>
using namespace std; Queue<T>::Queue(int MAX_SIZE) {
front = -1;
template <class T> back = -1;
class Queue { size = 0;
private: arr = new T[MAX_SIZE];
int front, back; }
T* arr;
int size; template <class T>
int MAX_SIZE; Queue<T>::~Queue() {
public: delete[] arr;
Queue(int MAX_SIZE); }
~Queue();
bool isEmpty(); template <class T>
bool isFull(); bool Queue<T>::isEmpty() {
void enqueue(T item); return (size == 0);
void dequeue(T& item); }
void retrieve(T& item);
void display(); template <class T>
int getSize(); bool Queue<T>::isFull() {
};
return (size == MAX_SIZE);
}
14
Queue (array-based implementation) (dynamic-array)
template <class T> template <class T>
void Queue<T>::enqueue(T item) { void Queue<T>::dequeue(T& item) {
if (isFull()) { if (isEmpty()) {
cout << "Error: Queue is full" << endl; cout << "Error: Queue is empty" << endl;
return; return;
} }
else if (isEmpty()) { else if (front == back) {
front = back = 0; item = arr[front];
} front = back = -1;
else { }
back = (back + 1) % MAX_SIZE; else {
}
item = arr[front];
arr[back] = item;
size++; front = (front + 1) % MAX_SIZE;
} }
template <class T> size--;
void Queue<T>::retrieve(T& item) { }
if (isEmpty()) {
cout << "Error: Queue is empty" << endl; template<class T>
return; int Queue<T>::getSize() {
} return size; }
item = arr[front];
}
15
Queue (array-based implementation) (dynamic-array)
template <class T>
void Queue<T>::display() {
if (isEmpty()) {
cout << "Queue is empty" << endl;
return;
}
int i = front;
while (i != back) {
cout << arr[i] << " ";
i = (i + 1) % MAX_SIZE;
}
cout << arr[back] << endl;
}

16
Queue
#include "Queue.h"
Save the previous implementation in Queue.h and Queue.cpp.
Then, write the following code in main.cpp #include <string>
#include <iostream>
using namespace std;

int main() {
Queue<int> q;

q.enqueue(100);
q.enqueue(200);
q.enqueue(300);
q.enqueue(400);

q.display();
int item;
q.dequeue(item);

q.display();

q.retrieve(item);
cout << "Element at front: " << item << endl;

return 0;
17
}
Queue
To demonstrate the use of queues, we first look at a simple problem: identifying
palindromes. A palindrome is a string that reads the same forward as backward. Identifying these strings
provides us with a good example for the use of both queues and stacks.
Some famous palindromes are:
“Madam”
“Eve.”
“ Level”
“ Radar”
“Pop”
“Won ton? Not now!”

18
Palindrome checking using queue
#include "Queue.h"
#include <string>
#include <iostream>
using namespace std;
// function to check if a given string is a palindrome
bool isPalindrome(string str) {
char ch1, ch2;
Queue<char> q; // create an instance of the Queue class to store the characters in the string
for (int i = 0; i < str.length(); i++) {
cout<<str[i]<<endl;
q.enqueue(str[i]); // enqueue the character to the queue
}
for (int i = 0; i < str.length(); i++) {
q.retrieve(ch1); // retrieve the character at the front of the queue
ch2 = str[str.length()-1-i]; // get the corresponding character from the end of the
string
if (ch1 != ch2) { // compare the two characters
return false; // if they are not the same, return false
}
q.dequeue(ch1); // dequeue the character from the queue
}
return true; // if all characters are the same, return true
19
}
Palindrome checking using queue
int main() {
string str;
cout << "Enter a string: ";
cin >> str;
if (isPalindrome(str)) {
cout << str << " is a palindrome." << endl;
}
else {
cout << str << " is not a palindrome." << endl;
}

return 0;
}

20
Palindrome checking using stack
#include "stdafx.h"
#include <iostream>
#include <string>
#include "stack.h"
using namespace std;
// Function to check if a string is a palindrome using a stack
bool isPalindromeA(string str) {
Stack<char> s;
// Push all the characters of the string onto the stack
for (int i = 0; i < str.length(); i++) {
s.push(str[i]);
}
char ch;
// Pop half of the characters from the stack and compare with the other half
for (int i = 0; i < str.length() / 2; i++) {
s.peek(ch);
if (ch!= str[i]) { // If the character on top of the stack does not match the
corresponding character in the string
return false; // The string is not a palindrome
}
s.pop(ch); // Remove the top character from the stack
}
return true; // if all characters are matched then the string is a palindrome
21
}
Palindrome checking using stack
int main() {
string str;
cout << "Enter a string: ";
cin >> str;

if (isPalindromeA(str)) {
cout << str << " is a palindrome" << endl;
} else {
cout << str << " is not a palindrome" << endl;
}
system("pause");
return 0;
}

22
Queue types
There are four different types of queue
 Simple Queue
 Circular Queue
 Priority Queue
 Double Ended Queue (or Deque)

Simple Queue
In simple Queue, an insertion takes place from one end while the deletion occurs from another end. The end at
which the insertion takes place is known as the rear end, and the end at which the deletion takes place is known as
front end. It strictly follows the FIFO rule.
The major drawback of using a linear Queue is that insertion is done only from the rear end. If the first three
elements are deleted from the Queue, we cannot insert more elements even though the space is available in a Linear
Queue. In this case, the linear Queue shows the overflow condition as the rear is pointing to the last element of the
Queue.

Circular Queue
In Circular Queue, all the nodes are represented as circular. It is similar to the simple Queue except that the last element
of the queue is connected to the first element. It is also known as Ring Buffer, as all the ends are connected to another
end. The representation of circular queue is shown in the below image -The drawback that occurs in a simple queue is
overcome by using the circular queue. If the empty space is available in a circular queue, the new element can be added
in an empty space by simply incrementing the value of rear. The main advantage of using the circular queue is better
memory utilization.
23
Queue types
Priority Queue
It is a special type of queue in which the elements are arranged based on the priority. It is a special type of queue data
structure in which every element has a priority associated with it. Suppose some elements occur with the same
priority, they will be arranged according to the FIFO principle.
Insertion in priority queue takes place based on the arrival, while deletion in the priority queue occurs based on the
priority. Priority queue is mainly used to implement the CPU scheduling algorithms.
There are two types of priority queue that are discussed as follows -
Ascending priority queue - In ascending priority queue, elements can be inserted in arbitrary order, but only
smallest can be deleted first. Suppose an array with elements 7, 5, and 3 in the same order, so, insertion can be done
with the same sequence, but the order of deleting the elements is 3, 5, 7.
Descending priority queue - In descending priority queue, elements can be inserted in arbitrary order, but only the
largest element can be deleted first. Suppose an array with elements 7, 3, and 5 in the same order, so, insertion can be
done with the same sequence, but the order of deleting the elements is 7, 5, 3.

24
Queue types
Deque (or, Double Ended Queue)
In Deque or Double Ended Queue, insertion and deletion can be done from both ends of the queue either
from the front or rear. It means that we can insert and delete elements from both front and rear ends of the
queue. Deque can be used as a palindrome checker means that if we read the string from both ends, then the
string would be the same.
Deque can be used both as stack and queue as it allows the insertion and deletion operations on both ends.
Deque can be considered as stack because stack follows the LIFO (Last In First Out) principle in which
insertion and deletion both can be performed only from one end. And in deque, it is possible to perform both
insertion and deletion from one end, and Deque does not follow the FIFO principle.
There are two types of deque that are discussed as follows -
Input restricted deque - As the name implies, in input restricted queue, insertion operation can be
performed at only one end, while deletion can be performed from both ends.
output restricted deque - As the name implies, in output restricted queue, deletion operation can be
performed at only one end, while insertion can be performed from both ends.

25

You might also like