0% found this document useful (0 votes)
73 views37 pages

Chapter 4: Stacks & Queues

This document summarizes key aspects of stacks and queues as data structures, including: 1) Stacks follow the last-in first-out (LIFO) principle and can be implemented using arrays. Pushing adds an element to the top of the stack and popping removes the top element. 2) Queues follow the first-in first-out (FIFO) principle and can also be implemented using arrays. Enqueuing adds an element to the back of the queue and dequeuing removes the front element. 3) Growable array implementations are needed for stacks and queues to dynamically increase the underlying array size to avoid overflow exceptions when the fixed-size array is full.

Uploaded by

JchristianOaxaco
Copyright
© Attribution Non-Commercial (BY-NC)
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PPT, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
73 views37 pages

Chapter 4: Stacks & Queues

This document summarizes key aspects of stacks and queues as data structures, including: 1) Stacks follow the last-in first-out (LIFO) principle and can be implemented using arrays. Pushing adds an element to the top of the stack and popping removes the top element. 2) Queues follow the first-in first-out (FIFO) principle and can also be implemented using arrays. Enqueuing adds an element to the back of the queue and dequeuing removes the front element. 3) Growable array implementations are needed for stacks and queues to dynamically increase the underlying array size to avoid overflow exceptions when the fixed-size array is full.

Uploaded by

JchristianOaxaco
Copyright
© Attribution Non-Commercial (BY-NC)
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PPT, PDF, TXT or read online on Scribd
You are on page 1/ 37

Chapter 4: Stacks &

Queues
Stacks & Queues

Acknowledgement:
These slides are adapted from slides provided with Data Structures and Algorithms in C++
Goodrich, Tamassia and Mount (Wiley, 2004)
Stacks
Outline and Reading
• The Stack ADT (§4.2.1)
• Applications of Stacks (§4.2.3)
• Array-based implementation (§4.2.2)
• Growable array-based stack

Elementary Data Structures 3


Abstract Data Types (ADTs)
• An abstract data • Example: ADT modeling a
type (ADT) is an simple stock trading system
abstraction of a • The data stored are buy/sell
data structure orders
• An ADT specifies: • The operations supported are
• Data stored • order buy(stock, shares, price)
• Operations on the • order sell(stock, shares, price)
data • void cancel(order)
• Error conditions • Error conditions:
associated with • Buy/sell a nonexistent stock
operations
• Cancel a nonexistent order

Elementary Data Structures 4


The Stack ADT (§4.2.1)
• The Stack ADT stores
arbitrary objects
• Insertions and deletions • Auxiliary stack
follow the last-in first-out operations:
(LIFO) scheme
• top(): returns the last
inserted element without
• Think of a spring-loaded removing it
plate dispenser • size(): returns the
• Main stack operations: number of elements
stored
• push(Object o): inserts
element o
• isEmpty(): a Boolean
value indicating whether
• pop(): removes and returns
no elements are stored
the last inserted element
Elementary Data Structures 5
Exceptions
• Attempting the • In the Stack ADT,
execution of an operations pop and
operation of ADT may top cannot be
sometimes cause an performed if the
error condition, called stack is empty
an exception • Attempting the
• Exceptions are said to execution of pop or
be “thrown” by an top on an empty
operation that cannot stack throws an
be executed EmptyStackException
Elementary Data Structures 6
Exercise: Stacks
• Describe the output of the following series of
stack operations
• Push(8)
• Push(3)
• Pop()
• Push(2)
• Push(5)
• Pop()
• Pop()
• Push(9)
• Push(1)

Elementary Data Structures 7


Applications of Stacks
• Direct applications
 Page-visited history in a Web browser
 Undo sequence in a text editor
 Saving local variables when one function calls
another, and this one calls another, and so on.
• Indirect applications
 Auxiliary data structure for algorithms
 Component of other data structures

Elementary Data Structures 8


C++ Run-time Stack
main() {
• The C++ run-time system int i;
keeps track of the chain of bar
i = 5;
active functions with a stack foo(i); PC = 1
• When a function is called, the } m=6
run-time system pushes on the foo(int j) {
stack a frame containing int k; foo
• Local variables and return value k = j+1; PC = 3
• Program counter, keeping track of bar(k); j=5
the statement being executed } k=6
• When a function returns, its bar(int m) {
frame is popped from the stack … main
} PC = 2
and control is passed to the
i=5
method on top of the stack
Elementary Data Structures 9
Array-based Stack
• A simple way of Algorithm size()
implementing the return t + 1
Stack ADT uses an
Algorithm pop()
array if isEmpty() then
• We add elements throw EmptyStackException
from left to right else
• A variable keeps tt1
track of the index of return S[t + 1]
the top element


S
0 1 2 t
Elementary Data Structures 10
Array-based Stack (cont.)
• The array storing the
stack elements may Algorithm push(o)
become full if t = S.length  1 then
• A push operation will throw FullStackException
then throw a else
FullStackException tt+1
 Limitation of the array- S[t]  o
based implementation
 Not intrinsic to the
Stack ADT

S …
0 1 2 t
Elementary Data Structures 11
Performance and Limitations
- array-based implementation of stack ADT

• Performance
• Let n be the number of elements in the stack
• The space used is O(n)
• Each operation runs in time O(1)
• Limitations
• The maximum size of the stack must be defined a
priori , and cannot be changed
• Trying to push a new element into a full stack
causes an implementation-specific exception

Elementary Data Structures 12


Growable Array-based
Stack
• In a push operation, when
the array is full, instead of
throwing an exception, we Algorithm push(o)
if t = S.length  1 then
can replace the array with a A  new array of
larger one size …
for i  0 to t do
• How large should the new A[i]  S[i]
array be? SA
tt+1
• incremental strategy: S[t]  o
increase the size by a
constant c
• doubling strategy: double the
size
Elementary Data Structures 13
Growable Array-based Stack
• In a push operation, when the Algorithm push(o)
array is full, instead of throwing if t = S.length  1 then
an exception, we can replace A  new array of
the array with a larger one size …
for i  0 to t do
• How large should the new array A[i]  S[i]
be? SA
• incremental strategy: increase the tt+1
size by a constant c S[t]  o
• doubling strategy: double the size

Elementary Data Structures 14


Comparison of the
Strategies

• We compare the incremental strategy and


the doubling strategy by analyzing the total
time T(n) needed to perform a series of n
push operations
• We assume that we start with an empty
stack represented by an array of size 1
• We call amortized time of a push operation
the average time taken by a push over the
series of operations, i.e., T(n)/n
Elementary Data Structures 15
Incremental Strategy Analysis
• We replace the array k = n/c times
• The total time T(n) of a series of n push operations is
proportional to
• n + c + 2c + 3c + 4c + … + kc =
• n + c(1 + 2 + 3 + … + k) =
• n + ck(k + 1)/2
• Since c is a constant, T(n) is O(n + k2), i.e., O(n2)
• The amortized time of a push operation is O(n)

Elementary Data Structures 16


Doubling Strategy Analysis
• We replace the array k = log2 n
times
geometric series
• The total time T(n) of a series of
n push operations is 2
proportional to 4
• n + 1 + 2 + 4 + 8 + …+ 2k = 1 1
• n  2k + 1 1 = 2n 1
8
• T(n) is O(n)
• The amortized time of a push
operation is O(1)
Elementary Data Structures 17
Stack Interface in C++
template <typename Object>
• Interface class Stack {
corresponding to public:
our Stack ADT int size();
• Requires the bool isEmpty();
Object& top()
definition of class
throw(EmptyStackException);
EmptyStackException void push(Object o);
• Most similar STL Object pop()
construct is vector throw(EmptyStackException);
};

Elementary Data Structures 18


Array-based Stack in C++
template <typename Object> bool isEmpty()
class ArrayStack { { return (t < 0); }
private:
int capacity; // stack capacity Object pop()
Object *S; // stack array throw(EmptyStackException) {
int top; // top of stack if(isEmpty())
public: throw EmptyStackException
ArrayStack(int c) { (“Access to empty stack”);
capacity = c; return S[t--];
S = new Object[capacity]; }
t = –1; // … (other functions omitted)
}

Elementary Data Structures 19


Queues
Outline and Reading
• The Queue ADT (§4.3.1)
• Implementation with a circular array
(§4.3.2)
• Growable array-based queue
• Linked List ADT
• List-based queue
• Queue interface in C++

Elementary Data Structures 21


The Queue ADT (§4.3.1)
• The Queue ADT stores • Auxiliary queue operations:
arbitrary objects • front(): returns the element
• Insertions and deletions follow at the front without removing
the first-in first-out (FIFO) it
scheme • size(): returns the number of
• Insertions are at the rear of elements stored
the queue and removals are • isEmpty(): returns a Boolean
at the front of the queue value indicating whether no
• Main queue operations: elements are stored
enqueue(object o): inserts
• Exceptions

element o at the end of the


queue • Attempting the execution of
• dequeue(): removes and dequeue or front on an
returns the element at the empty queue throws an
front of the queue EmptyQueueException

Elementary Data Structures 22


Exercise: Queues
• Describe the output of the following series of
queue operations
• enqueue(8)
• enqueue(3)
• dequeue()
• enqueue(2)
• enqueue(5)
• dequeue()
• dequeue()
• enqueue(9)
• enqueue(1)

Elementary Data Structures 23


Applications of Queues
• Direct applications
• Waiting lines
• Access to shared resources (e.g., printer)
• Multiprogramming
• Indirect applications
• Auxiliary data structure for algorithms
• Component of other data structures

Elementary Data Structures 24


Array-based Queue
• Use an array of size N in a circular fashion
• Two variables keep track of the front and rear
• f index of the front element
• r index immediately past the rear element
• Array location r is kept empty

normal configuration
Q
0 1 2 f r

wrapped-around configuration
Q
0 1 2 r f
Elementary Data Structures 25
Queue Operations
• We use the Algorithm size()
return (N - f + r) mod N
modulo operator
(remainder of Algorithm isEmpty()
return (f = r)
division)

Q
0 1 2 f r
Q
0 1 2 r f

Elementary Data Structures 26


Queue Operations (cont.)
• Operation enqueue throws Algorithm enqueue(o)
an exception if the array is if size() = N  1 then
full throw FullQueueException
• This exception is else
implementation-dependent Q[r]  o
r  (r + 1) mod N

Q
0 1 2 f r
Q
0 1 2 r f

Elementary Data Structures 27


Queue Operations (cont.)
• Operation dequeue Algorithm dequeue()
throws an exception if isEmpty() then
throw EmptyQueueException
if the queue is empty
else
• This exception is o  Q[f]
specified in the f  (f + 1) mod N
queue ADT return o

Q
0 1 2 f r
Q
0 1 2 r f
Elementary Data Structures 28
Performance and Limitations
- array-based implementation of queue ADT

• Performance
• Let n be the number of elements in the stack
• The space used is O(n)
• Each operation runs in time O(1)
• Limitations
• The maximum size of the stack must be defined a
priori , and cannot be changed
• Trying to push a new element into a full stack
causes an implementation-specific exception

Elementary Data Structures 29


Growable Array-based Queue
• In an enqueue operation, when the array is
full, instead of throwing an exception, we
can replace the array with a larger one
• Similar to what we did for an array-based
stack
• The enqueue operation has amortized
running time
• O(n) with the incremental strategy
• O(1) with the doubling strategy

Elementary Data Structures 30


Singly Linked List
(we will formalize List ADT in Ch. 5)
• A singly linked list is a
concrete data structure next
consisting of a sequence
of nodes
• Each node stores
• element elem node
• link to the next node

A B C D

Elementary Data Structures 31


Queue with a Singly Linked List
• We can implement a queue with a singly linked list
• The front element is stored at the first node
• The rear element is stored at the last node
• The space used is O(n) and each operation of the Queue ADT takes O(1)
time
• NOTE: we do not have the limitation of the array based implementation on
the size of the stack b/c the size of the linked list is not fixed, I.e., the
deque is NEVER full.
r
nodes

f 

elements
Elementary Data Structures 32
Informal C++ Queue Interface
template <typename Object>
• Informal C++ class Queue {
interface for our public:
Queue ADT int size();
• Requires the bool isEmpty();
Object& front()
definition of class
throw(EmptyQueueException);
EmptyQueueException void enqueue(Object o);
• No corresponding Object dequeue()
built-in STL class throw(EmptyQueueException);
};

Elementary Data Structures 34


The Double-Ended Queue ADT
(§4.5.1)
• The Double-Ended Queue, or • Auxiliary queue operations:
Deque, ADT stores arbitrary • first(): returns the element at
objects. (Pronounced ‘deck’) the front without removing it
• Richer than stack or queue ADTs. • last(): returns the element at the
Supports insertions and deletions front without removing it
at both the front and the end.
• size(): returns the number of
• Main deque operations: elements stored
• insertFirst(object o): inserts
element o at the beginning of the
• isEmpty(): returns a Boolean
deque value indicating whether no
• insertLasst(object o): inserts elements are stored
element o at the end of the • Exceptions
deque
• Attempting the execution of
• RemoveFirst(): removes and
returns the element at the front dequeue or front on an empty
of the queue queue throws an
• RemoveLast(): removes and EmptyDequeException
returns the element at the end of
the queue

Elementary Data Structures 35


Doubly Linked List
(we will formalize List ADTs in Ch. 5)
• A doubly linked list provides a natural prev next
implementation of the Deque ADT
• Nodes implement Position and store:
• element
• link to the previous node elem node
• link to the next node
• Special trailer and header nodes

header nodes/positions trailer

elements
Elementary Data Structures 36
Deque with a Doubly Linked List
• We can implement a deque with a doubly linked list
• The front element is stored at the first node
• The rear element is stored at the last node
• The space used is O(n) and each operation of the
Deque ADT takes O(1) time

first last

elements
Elementary Data Structures 37
Performance and Limitations
- doubly linked list implementation of deque ADT

• Performance
• Let n be the number of elements in the stack
• The space used is O(n)
• Each operation runs in time O(1)
• Limitations
• NOTE: we do not have the limitation of the array
based implementation on the size of the stack b/c
the size of the linked list is not fixed, I.e., the
deque is NEVER full.

Elementary Data Structures 38

You might also like