Module 2_2022 Scheme
Module 2_2022 Scheme
QUEUES AND
LINKED LISTS
CONTENTS
QUEUES
Queues
Circular Queues
Using Dynamic Arrays
Multiple Stacks and queues.
LINKED LISTS
Singly Linked Lists
Lists and Chains
Representing Chains in C
Linked Stacks and Queues
Polynomials
QUEUES
Like a Stack, a Queue is also an ordered list of items.
f r
Delet
e
0 1 2 3 4 Deleted
C D element is B
f r
Delet
0 1 2 3 4 Deleted
e
D element is C
f, r
Delet
e
0 1 2 3 4 Deleted
element is D
QUEUES
ADT Queue is
objects: a finite ordered list with zero or more elements
functions: for all queue Є Queue, item Є element, maxQueueSize Є
positive integer
Queue CreateQ(maxQueueSize) ::= create an empty queue whose maximum
sixe is maxQueueSize.
Boolean IsFullQ(queue, maxQueueSize) ::= if(number of elements in queue
== maxQueueSize)
return TRUE else return FALSE. Queue
AddQ(queue, item) ::= if(IsFullQ(queue)) queue full
else insert item at the rear of queue and return queue
Boolean IsEmptyQ(queue) ::=
if(queue == CreateQ(maxQueueSize)) return TRUE
else return FALSE.
Element DeleteQ(queue) ::= if(IsEmptyQ(queue) ) return
else remove and return the item at front of the queue.
QUEUES
Array representation of Queue
Queues are represented using a linear array with two indices
namely Front and Rear.
Display
Printf(“Overflow”);
else{
Rear = Rear + 1;
Queue[Rear] =
QUEUES
Queue
Deletion int deleteQ (){
if(Front == Rear)
Printf(“Underflow”);
else{
Front= Front +
1;
return
Queue Queue[Front];
Display void displayQ
} (){
int i;
for(i = Front+1;
i<=Rear; i++)
printf(“%d”,
QUEUES
Disadvantage of a Linear Queue
Consider the following queue
1 2 3 4
Front =
0
Rear =
We now perform some insertions and deletions on this queue.
0
1 2 3 4
Front = AAA BBB CCC DDD
2
0
1
Rear =
Now the question
1 is, Can we insert another element in the
4
2
3
queue?
2
A circular queue is presented below.
3
1 2 3 …. MA
X 1
Linear Queue …
MA Circular
CIRCULAR QUEUE
This circular representation helps us to easily overcome
the problem that we encountered in a linear queue.
Now the task is to bring the rear index from its current
position 5 to index 1.
CIRCULAR QUEUE
We simply cannot increment the value
of r as this will result in r=6, which is
2
not a valid index position in the circular
queue.
2 3
0 3
1 0 In circular queue, we use the %
operator to perform the increment.
4
0 4
50
The increment operation is performed
5
as,
f = 1, r r = (r+1) % MAX
=5
In our example
r = (r+1) % MAX
r = (5+1) % 5 = 6 % 5= 1
CIRCULAR QUEUE
Similarly the front index is also incremented as,
f = (f +1)% MAX;
The queue is now full. The position of rear index is, r = MAX. Hence
this can be considered as the condition to check for overflow.
CIRCULAR QUEUE
2
2 3
0 3
f = 1,
0, r 1 1 0
6
=15 0
0 4
0
5 4
0
5
Let us now delete an item from the above queue.
With one free space available, we can insert another element
in the circular queue. On doing so, we get the above queue.
We see that the queue is full again. However, what we
need to observe is the values of f and r.
f = r and the queue is full. Earlier, we used the same condition
to check if queue is empty. This is a contradiction.
CIRCULAR QUEUE
Hence, we can conclude that, in circular queues, the
overflow and underflow conditions cannot be
determined based on the positions of indices f and r.
printf(“Overflow”); printf(“Underflow”);
else{ else{
r = (r+1) % f = (f+1) %
MAX ; MAX ;
Q[r] = item; return Q[f];
count++; count- -;
} }
} }
CIRCULAR QUEUES USING DYNAMIC ARRAYS
We go for dynamic allocation of circular queues to
overcome the drawbacks that exist in static allocation.
Segment Segment
1 2
Step 1
Create a new array newQueue whose size is twice the capacity.
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
Step 2
Copy the second segment (from queue[f+1] to queue[capacity –
1]) in the newQueue beginning at 0.
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
A B
CIRCULAR QUEUES USING DYNAMIC ARRAYS
Step 3
Copy the first segment(from queue[0] to queue[rear]) in
newQueue beginning at capacity – f – 1.
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
A B C D E F G
Step 4
Reorganize indices f and r.
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
A B C D E F G
r f
Now it is possible to comfortably add 8 more elements into the above
queue.
queu 0 1 2 3 4 5 6 7 capacity
e
00 0 0 0 0 0 0 0 0 =8
0 1 2 3 4 5 6 7 rear = 4
C D E F G A B front = 5
r f
0 1 2 3 4 5 6 7 8 9 1 …….. 1
newQue
0 5
ue
70 7 7 7 7 7 7 7 7 7 7 8 ………. 8
0 1 2 3 4 5 6 7 8 9 0 5
A B
Next we copy the first segment and place the
elements in newQueue.
newQue 0 1 2 3 4 5 6 7 8 9 1 …….. 1
0 5
ue
70 7 7 7 7 7 7 7 7 7 7 8 ………. 8
0 1 2 3 4 5 6 7 8 9 0 5
A B C D E F G
CIRCULAR QUEUES USING DYNAMIC ARRAYS
The next set of statement adjust the positions of f and
r in newQueue.
queu 0 1 2 3 4 5 6 7
e
70
00 0 0 0 0 0 0 0 0
0 1 2 3 4 5 6 7
C D E F G
r f A B
0 1 2 3 4 5 6 7 8 9 1 …….. 1
0 5
newQue
7 7 7 7 7 7 7 7 7 7 8 ………. 8
ue
70 0 1 2 3 4 5 6 7 8 9 0 5
r f
A B C D E F G
MULTIPLE STACKS AND QUEUES
Here we attempt to represent more than one stack in a 1D array.
0 1 2 3 4 5 6 7 8 9 1 1 1 1 1 1 1 1 1 1
0 1 2 3 4 5 6 7 8 9
s[MAX_SIZ
E]
Consider that the above array must accommodate n =
4 stacks.
Hence, the size of each stack is 5. The array now looks like,
0 1 2 3 4 5 6 7 8 9 1 1 1 1 1 1 1 1 1 1
0 1 2 3 4 5 6 7 8 9
0 1 2 3 4 5 6 7 8 9 1 1 1 1 1 1 1 1 1 1
0 1 2 3 4 5 6 7 8 9
Overflow condition
Let us push 5 elements in each of the four stacks. The
resulting array is,
0 1 2 3 4 5 6 7 8 9 1 1 1 1 1 1 1 1 1 1
0 1 2 3 4 5 6 7 8 9
A E I M Q B F J N R C G K O S D H L P T
Stack 0 Stack 1 Stack 2 Stack 3
0
-1
top[0] = 1
2
3
4 5
4
top[1] = 6
7
8
9 9
11
10
12
13
top[2] = 14 15
14
top[3] = 16
17
18
19
boundary[0] boundary[1] boundary[2] boundary[3]
= -1 =4 =9 = 14
Hence, when the top of ith stack is at the same position as
boundary of (i+1)th stack, then we say that stack i is full.
MULTIPLE STACKS AND QUEUES
The code for overflow condition in multiple stacks is,
if(top[ i ] = = boundary[ i +
1 ]){
printf(“stack %d is
full”, i);
Underflow } condition
Underflow condition is comparatively easy to define.
Stack 0 Stack 1 Stack 2 Stack 3
0 1 2 3 4 5 6 7 8 9 1 1 1 1 1 1 1 1 1 1
0 1 2 3 4 5 6 7 8 9
push(10,
pop(2)
push(15,
push(25,
push(35, 35 is popped from
MULTIPLE STACKS AND QUEUES
Display operation
void display(int i){
if(top[ i ] = = boundary[ i ]){
printf(“stack %d is empty”, i);
}else{
for( j = boundary[i] + 1; j<= top[
i ]; j++){
printf(“%d”, s[j]);
}
}
Stack 0 Stack 1 Stack 2 Stack 3
0 1 2 3 4 5 6 7 8 9 1 1 1 1 1 1 1 1 1 1
0 1 2 3 4 5 6 7 8 9
1 1 2 3
0 top[0]
5 = -1
0
1 top[1] = 4 5 top[2]
5 = 11
9
10 top[3] = 14
boundary[0] boundary[1] boundary[2] boundary[3]
= -1 =4 =9 = 14
display(
LINKED LIST
One way by which we can store a list of items is using arrays,
in which every item is stored in consecutive memory
locations.
Also every item will have a field called link, that contains the
address of the next item in the list.
LINKED LIST
This means, we need not store successive items of the list in
successive memory locations.
However, with linked list, the sequence need not be the same as
mentioned.
LINKED LIST
Each node in a linked list is divided into two parts:
info - contains the information about the element
link – contains the address of the next node in the list
STAR
T info link
The info part of a node can either contain a single data item or a
group of data items.
The link part holds the address of the next node in the list.
The linked list also has a list pointer, called START, that points to the
first node of the list. START indicates the beginning of the list.
REPRESENTATION OF LINKED LISTS IN MEMORY
Since a simple linked list is made up of two parts(info and link),
a linked list is maintained using two linear arrays in the memory.
The second array is called the LINK array and it contains the
addresses of next nodes in the linked list.
The list also requires a variable, called START, that points to the
first node of the list.
REPRESENTATION OF LINKED LISTS IN MEMORY
Consider the following linked list.
STAR
T N O E X I T X
6 3 62 8
4 74 9
5
6 88 10
7 82 0
GEO 8 74 1
M1 9 78 0
1 1 74 2
0
84 3
1
INFO LINK
REPRESENTATION OF LINKED LISTS IN MEMORY
Array representation of multiple lists
BON
D Gra Scot Vit Kat X
nt t o z
KELL
Y Hunt McBri Eva X
er de ns
HAL
L
X
NELSO
N Tell Jone Ada Roge West X
er s ms rs on
REPRESENTATION OF LINKED LISTS IN MEMORY
1 Vito 4
2
3 Hunter 14
4 Katz 0
5
1 BOND 12 6 Evans 0
2 KELLY 3 7
3 HALL 0 8 Rogers 15
4 NELSON 9 9 Teller 10
1 Jones 17
Facult Link 0
y 1
1 Grant 16
1
2 McBride 6
1 Weston 0
3
Scott 1
1
4 Adams 8
1 Stude Link
REPRESENTATION OF LINKED LISTS IN MEMORY
Representation of lists with multiple data items in each node.
STAR
T Bro 1785210 Fema 1470 Coh 1774445 Male 1900
wn 65 le 0 en 57 0
Along with the data, there is a link part that contains the
address/index of the next node.
Info link
1002
1000 1001 1002 1003 1004 1005 1006
ptr
REPRESENTATION OF LINKED LISTS IN MEMORY
Assigning values to a node
Once a node has been created, we next need to fill the
node with appropriate values.
It is represented by a pointer.
node* ptr;
ptr = (node*)malloc(sizeof(node));
Info link
1002
1000 1001 1002 1003 1004 1005 1006
ptr
1000 2000
1000 A 1000
200 B 2000
300
\0 3000
1000
STAR A 2000 B TEMP0
300 C \0
TEMP
T
TEMP
STAR 0 0 3000
T 3000 C \0
NEW
1000 2000
1000 A 200 B 300
STAR 0 0
TEMP
T 3000
3000 C \0
NEW
2000
1000 A 200 B 300 C \0
STAR 0
TEMP 0
T
node* deletFront(node*
start){
} node* temp;
temp = start;
} start = start link;
} free(temp);
return start;
}
LINKED LIST OPERATIONS
Deleting a specified node
1000 2000
3000 3000
1000 200
A 300 C
B \0300 C \0
STAR TEMP0 TEMP0
PREV
T
1000
1000 2000
3000 3000
1000
1000 AA 300
200
300 B
C 300\0 C \0
STAR 00
TEMP
PREV TEMP 0
STAR
TT
node* deleteSpecific(node
deleteSpecific(node* prev link = temp
*start, charkey){
start, char key){ link;
} node *temp, *prev; free(temp);
temp = start; prev = return start;
NULL; }
} while(temp != NULL){
if(temp info ==
key)
break;
prev = temp;
temp = temp link;
}
LINKED LIST OPERATIONS
Deleting the last node of the list
1000
1000 2000
2000 3000
1000
1000 AA 200
200 BB 300
\0
\0 C \0
STAR
STAR TEMP
PREV00 TEMP
PREV0 TEMP
TT
node* deleteEnd(node*
start){
} node *temp, *prev;
temp = start; prev =
= NULL;
NULL;
} while(temp link !=
NULL){
prev = temp;
temp = temp
link;
}
} free(temp);
LINKED LIST OPERATIONS
Displaying contents of a list
1000 2000 3000
1000 A 200 B 300 C \0
STAR 0
TEMP 0
TEMP TEMP
T
40 To
p 400 300 200 100
30
400 400 300 200 100 \0
20 0
To
p Linked List representation of the Stack
10
Stack[4
]
LINKED STACKS AND QUEUES
Linked Stack operations
Like in normal stacks, Push and Pop are the operations
that are performed on linked stacks as well.
PUSH
One difference between normal stacks and linked
stacks is the overflow condition.
struct node{
int info;
struct node
*link;
};
The Push operation is implemented as follows.
3 TEM
100200P 100
2 0 \0 0100
200
100 1020 100 \0
1 20 To 0 0
TOP
p
0 10 To
p
Stack[4
]
STEP 1 – Print the STEP 1 – Create a TEMP
element pointed pointer. Make TEMP point
by Top. to TOP node.
STEP 2 – STEP 2 – Make TOP point
Decrement the to the next node.
LINKED STACKS AND QUEUES
TEM
100200P 100
200
100 0 \0 0100
1020 100 \0
0 0
TOP
Queue[ 20 30 40
4] fro rea
nt r
Insertion
Queue[ 200 300 400
4] 200 200 300 \0 400 \0
20 30 40
0
Fro Rea NE
Rea
Rea
fro rea nt r W
rr
nt r
rear
STEP 1 – Create a NEW
STEP 1 – Increment
node.
Rear.
STEP 2 – Make Rear node
STEP 2 – Insert the
point to the NEW node.
new element at
STEP 3 – Make Rear point to
the position
the NEW node.
LINKED STACKS AND QUEUES
200 300 400
200 300 400
200 2000 300 400 \0
200 20 300 \0 400 \0
0
Fro Rea
0
Fro Rea ne
nt r
nt r w
Queue[
300 400
4]
20 30 40 200 300 400
300 200 300 400 \0
300
200 300 400 \0
fro rea 0
0 Fro TEM
Fro Rea
Rea
nt
front r nt r
nt P r
STEP 1 – STEP 1 – Create a TEMP
Increment Front. pointer. Make TEMP point to
STEP 2 – Delete the first node.
the element STEP 2 – Make Front point to
pointed by the second node.
Front. STEP 3 – Delete the TEMP
node.
LINKED STACKS AND QUEUES
300 400
200 300 400
300 200 300 400 \0
300
200 300 400 \0
0
0 Fro TEM
Fro Rea
Rea
nt P r
nt r
Polynomial Representation
One condition that must be fulfilled for the representation
is that, the exponents of the given polynomial must be in
the decreasing order.
struct term{
int coef, expon; expo
coef link
struct term *link; n
}; polyno
typedef struct term de
polynode;
APPLICATION OF LINKED LISTS
The polynomials
a= + +
b= - +
are represented as follows,
polynode *a, *b;
b
b 4000
4000 5000
5000 6000
6000
400
400 8
8 14
14 5000
5000 -3
-3 10
10 6000
6000 10
10 66 \0
\0
0
0 TempB TempB
TempB
TempB
cc 1100
1100 1200
1200 1300
1300 1400
110
NUL
110 11
11 1
11 1 \0
1 1200
1200 -3
-3 1 \0
1 1300
1300 2
2 8
8 \0
\0
140 10 6 \0
0
L0 4
4
4 0
0 0
Temp Temp Temp Temp
end
end
end end
end end
TempA->expon <
>
= TempB-
>expon
END OF
MODULE 2