Priority Queues (Heaps)
Priority Queues (Heaps)
Therefore all the elements are either arranged in an ascending or descending order.
So, a priority Queue is an extension of the queue with the following properties.
• Every item has a priority associated with it.
• An element with high priority is dequeued before an element with low priority.
• If two elements have the same priority, they are served according to their order in the queue.
(the priority queue follows the first-in-first-out principle for de queue operation).
In the below priority queue, an element with a maximum ASCII value will have the highest priority.
The elements with higher priority are served first.
45 35 20 12 8 4
In the above table, 4 has the lowest priority, and 45 has the highest priority.
Priority Queue implementation using an array is one of the basic methods to implement a queue. In
this element, it is inserted and deleted based on its priority. The elements in the priority queue have
some priority. The priority of the element is used to determine the order in which the elements will
be processed.
We can store a heap in an array by mapping its elements row by row – from top left to bottom right
– to the array:
In a min-heap, the smallest element is always at the top, i.e., in the array, it is always at the first
position. This is why, when you print a Java PriorityQueue as a string, you see the smallest element
on the left. What you see is the array representation of the min-heap underlying the PriorityQueue
❖ In the function insert_element(), initially check if the queue is full. If it is, then print the
result as "Queue Overflow". If not, take the number to be inserted as input and insert a new
element into the priority queue.
❖ In the function delete_element(), firstly check if the queue is empty. If it is, then print the
result as "Queue Underflow". Otherwise, remove the element and the priority from the
front of the queue.
❖ In the function display_priorityqueue(), using for loop print all the elements of the queue
starting from front to rear.
❖ The function check_priority() is used to check the priority and place element.
#include <stdio.h>
#include <stdlib.h>
#define MAX 10
void create_queue();
void insert_element(int);
void delete_element(int);
void check_priority(int);
void display_priorityqueue();
int pqueue[MAX];
int front, rear;
void main()
{
int n, choice;
printf("\nEnter 1 to insert element by priority ");
printf("\nEnter 2 to delete element by priority ");
printf("\nEnter 3 to display priority queue ");
printf("\nEnter 4 to exit");
create_queue();
while (1)
{
printf("\nEnter your choice : ");
scanf("%d", &choice);
switch(choice)
{
case 1:
printf("\nEnter element to insert : ");
scanf("%d",&n);
insert_element(n);
break;
case 2:
printf("\nEnter element to delete : ");
scanf("%d",&n);
Input
Output
Operations
• Push: Pushing/inserting a new item in the priority queue at a position in accordance with
its priority
• Pop: Popping/removing a new item in the priority queue in accordance with its priority
Heap data structure can be used to implement a priority queue. A heap data structure should not be
confused with the heap, a pool of memory used for dynamic memory allocation. A common
implementation of a heap is the binary heap, which is defined as a binary tree with two additional
properties:
Properties of Heap
All right, now with the basics out of the way, let's take a closer look at the specific properties of the
heap data structure.
1. Ordering
Nodes must be arranged in an order according to values. The values should follow min-heap or
max-heap property.
In min-heap property, the value of each node, or child, is greater than or equal to the value of its
parent, with the minimum value at the root node.
Min-heap
Max-heap
2. Structural
All levels in a heap should be full. In other words, it should be a complete binary tree:
The complete binary tree maps the binary tree structure into the array indices, where each array
index represents a node. The index of the left or the right child of the parent node is simple
expressions. For a zero-based array, the root node is stored at index 0. If i is the index of the current
node, then,
floor() function always rounds down and returns the largest integer less than or equal to a given
number.
Suppose there are N Jobs in a queue to be done, and each job has its own priority. The job with
maximum priority will get completed first than others. At each instant, we are completing a job with
maximum priority and at the same time we are also interested in inserting a new job in the queue with
its own priority.
Note: An array can be used to simulate a tree in the following way. If we are storing one element at
index i in array Arr, then its parent will be stored at index i/2 (unless its a root, as root has no parent)
and can be accessed by Arr[i/2], and its left child can be accessed by Arr[2∗i] and its right child can
be accessed by Arr[2∗i+1]. Index of root will be 1 in an array.
a) Process of Insertion:
Elements can be inserted to the heap following a similar approach for deletion. The idea is to:
• First increase the heap size by 1, so that it can store the new element.
• Insert the new element at the end of the Heap.
• This newly inserted element may distort the properties of Heap for its parents. So, in order to
keep the properties of Heap, heapify this newly inserted element following a bottom-up
approach.
We shall use the same example to demonstrate how a Max Heap is created. The procedure to create
Min Heap is similar but we go for min values instead of max values.
We are going to derive an algorithm for max heap by inserting one element at a time. At any point of
time, heap must maintain its property. While insertion, we also assume that we are inserting a node in
an already heapified tree.
Step 1 − Create a new node at the end of heap.
Step 2 − Assign new value to the node.
Step 3 − Compare the value of this child node with its parent.
Step 4 − If value of parent is less than child, then swap them.
Step 5 − Repeat step 3 & 4 until Heap property holds.
Note − In Min Heap construction algorithm, we expect the value of the parent node to be less than
that of the child node.
The item at the root of the heap has the highest priority among all elements. If we want to add a
new node to a binary heap, we need to ensure that our two properties of the heap are
maintained after the new node is added. At first, we insert the new item at the end of the
priority queue. If it is found greater than its parent node, elements are swapped. This process
continues until the new item is placed in the correct position. Let’s go through an example to
understand the insertion process. If we add to the priority queue, we end up with:
Now, we
notice that is smaller than its parent, so we stop and reach our priority queue:
The
If we insert an element in a priority queue, it will move to the empty slot by looking from top to
bottom and left to right.
If the element is not in a correct place then it is compared with the parent node; if it is found out of
order, elements are swapped. This process continues until the element is placed in a correct position.
b) Deletion in Heap
Given a Binary Heap and an element present in the given Heap. The task is to delete an element from this Heap.
The standard deletion operation on Heap is to delete the element present at the root node of the
Heap. That is if it is a Max Heap, the standard deletion operation will delete the maximum
element and if it is a Min heap, it will delete the minimum element.
An algorithm to delete from max heap. Deletion in Max (or Min) Heap always happens at the root to
remove the Maximum (or minimum) value.
Step 1 − Remove root node.
Step 2 − Move the last element of last level to root.
Step 3 − Compare the value of this child node with its parent.
Step 4 − If value of parent is less than child, then swap them.
Step 5 − Repeat step 3 & 4 until Heap property holds.
The root node is the item with the highest priority in a max heap. When removing the root node, we
replace it with the last item of the priority queue. Then, this item is compared with the child nodes
and swap with the greater one. It keeps moving down the tree until the heap property is restored.
Now, let’s apply to an example to understand how this process works. First, we replace the root
node with the last item :
The new priority queue is now violent the max heap’s property where the root node is smaller than
its children:
Now, is greater than its child of , we stop and reach our priority queue:
Priority queues are widely applied on other algorithms as well as in real-world systems. The main
applications include:
• Easy to implement
• Processes with different priorities can be handled efficiently
• Application with differing requirements
Conclusion
Identifying the priorities and doing tasks accordingly allows you with faster and effective results.
Priority queue is one such data structure that helps you arrange your data according to your priority
and make your tasks easy.
D-heaps;
A d-heap (sometime called a d-ary heap) data structure is similar to a binary heap. A binary heap is
actually a special case of the d-heap data structure where d = 2. Here is an example of min binary
heap on the left and max binary heap on the right:
The only difference between a binary heap and the d-heap is that instead of each node have 2
children, each node has d children.