Lab 3 – Array-Based Stack and Queue Overview In this assignment,
you will be implementing your own Array-Based Stack (ABS) and
Array-Based Queue (ABQ). A stack is a linear data structure which
follows the Last-In, First-Out (LIFO) property. LIFO means that the
data most recently added is the first data to be removed. (Imagine
a stack of books, or a stack of papers on a desk—the first one to
be removed is the last one placed on top.)
A queue is another linear data structure that follows the First-In,
First-Out (FIFO) property. FIFO means that the data added first is
the first to be removed (like a line in a grocery store—the first
person in line is the first to checkout).
Both of these are data structures—some sort of class to store
information. What makes them different is how they store and access
the information. Adding the same values (say, the numbers 1-10) to
either data structure would result in different ordering/output of
the information. Why you might choose one or the other depends on
the specific needs of a program. New keywords/language concepts
Templates – write code to work with multiple data types The Big
Three – Copy Constructor, Copy Assignment Operator, and Destructor
– necessary when working with dynamic memory Exceptions – Used to
indicate something went wrong in an application. Unhandled
exceptions will cause a program to terminate Deep copy – Creating
a copy of dynamically allocated memory requires new memory to be
allocated before copying values Stack Behavior Stacks have two
basic operations (with many other functions to accomplish these
tasks): Push – Add something to the top of the stack. Pop – Remove
something from the top of the stack and return it.
Example of LIFO operations-the data most recently added is the
first to be removed
COP3503 Programming Fundamentals 2 University of Florida
Queue Behavior Like a stack, a queue has two basic operations:
Enqueue – Add something to end of the queue. If this were a line, a
new person getting into the line would start at the back. Dequeue –
Remove something from the front of the queue. If this were a line,
the person at the start of the line is next—for whatever the people
are lining up for.
Example of FIFO operations-the newest data is last to be removed
Description Your ABS and ABQ will be template classes, and thus
will be able to hold any data type. (Many data structures follow
this convention—reuse code whenever you can!) Because these classes
will be using dynamic memory, you must be sure to define The Big
Three: Copy Constructor Copy Assignment Operator
Destructor
Data will be stored using a dynamically allocated array (hence the
array-based stack and queue). You may use any other
variables/function in your class to make implementation
easier.
The nature of containers like these is that they are always
changing size. You have 3 elements in a stack, and push() another…
now you need space for 4 elements. Use push() to add another, now
you need space for 5, etc… If your container is full, you can
increase the size by an amount other than one, if you want.
Why increase (or decrease) the size by any amount other than one?
Short answer: performance!
If you are increasing or decreasing the size of a container, it’s
reasonable to assume that you will want to increase or decrease the
size again at some point, requiring another round of allocate,
copy, delete, etc.
Increasing the capacity by more than you might need (right now) or
waiting to reduce the total capacity allows you to avoid costly
dynamic allocations, which can improve performance—especially in
situations in which this resizing happens frequently. This tradeoff
to this approach is that it will use more memory, but this
speed-versus-memory conflict is something that programmers have
been dealing with for a long time.
COP3503 Programming Fundamentals 2 University of Florida By
default, your ABS and ABQ will have a scale factor 2.0f—store this
as a class variable.
1. Attempting to push() or enqueue() an item onto an ABS/ABQ that
is full will resize the current capacity to
current_capacity*scale_factor. 2. When calling pop() or dequeue(),
if the “percent full” (e.g. current size / max capacity) becomes
strictly less than 1/scale_factor, resize the storage array to
current_capacity/scale_factor.
An example of the resizing scheme to be implement on a stack.
Resizing arrays What’s easy to say isn’t usually easy to do in
programming. You can’t “just” change the size of an array. You have
to: 1. Create a new array based on the desired size 2. Copy
elements from the old array to the new array (up to the size of the
old array, or the capacity of the new array, WHICHEVER IS SMALLER).
3. If you were adding something to the array, copy that as well 4.
Delete the old array 5. Redirect the pointer to the old array to
the new array Exceptions Some of your functions will throw
exceptions. There are many types of exceptions that can be thrown,
but in this case you will simply throw errors of type
runtime_error. This is a general purpose error to indicate that
something went wrong. The basic syntax for throwing an error is
simply:
throw type_of_exception("Message describing the error.");
If you wanted to throw a runtime_error exception that said “An
error has occurred.” you would write:
throw runtime_error("An error has occurred.");
There is also the concept of using try/catch blocks, but for this
assignment you will only have to throw the exceptions. Checking for
such exceptions will be handled by various unit tests on
zyBooks.
COP3503 Programming Fundamentals 2 University of Florida
Stack Functions Your ABS must support the following methods:
Method Description ABS() Default constructor. Maximum capacity
should be set to 1, and current size set to 0;
ABS(int capacity) Constructor for an ABS with the specified
starting maximum capacity.
ABS(const ABS &d) Copy Constructor
ABS &operator=(const ABS &d) Assignment operator.
~ABS() Destructor
void push(T data) Add a new item to the top of the stack and resize
if necessary.
T pop() Remove the item at the top of the stack, resizes if
necessary, and return the value removed. Throws a runtime_error if
the stack is empty.
T peek() Return the value of the item at the top of the stack,
without removing it. Throws a runtime_error if the stack is
empty.
unsigned int getSize() Returns the current number of items in the
ABS.
unsigned int getMaxCapacity() Returns the current max capacity of
the ABS.
T* getData() Returns the array representing the stack.
Additional methods may be added as deemed necessary.
COP3503 Programming Fundamentals 2 University of Florida
Queue Functions Your ABQ must support the following functions
Method Description ABQ() Default constructor. Maximum capacity
should be set to 1, and current size set to 0;
ABQ(int capacity) Constructor for an ABQ with the specified
starting maximum capacity.
ABQ(const ABS &d) Copy Constructor
ABQ &operator=(const ABQ &d) Assignment operator.
~ABQ() Destructor
void enqueue(T data) Add a new item to end of the queue and resizes
if necessary.
T dequeue() Remove the item at front of the queue, resizes if
necessary, and return the value removed. Throws a runtime_error if
the queue is empty.
T peek() Return the value of the item at the front of the queue,
without removing it. Throws a runtime_error if the queue is
empty.
unsigned int getSize() Returns the current number of items in the
ABQ.
unsigned int getMaxCapacity() Returns the current max capacity of
the ABQ.
T* getData() Returns the array representing the queue.
Additional methods may be added as deemed necessary.
COP3503 Programming
// C++ program to create Array based stack and array based queue classes
#include <iostream>
using namespace std;
template <class T>
class ABS
{
private:
static double scale;
unsigned int size;
unsigned int capacity;
T *data;
void resize(double scale);
public:
ABS();
ABS(int capacity);
ABS(const ABS &d) ;
ABS &operator=(const ABS &d);
~ABS() ;
void push(T data);
T pop();
T peek() ;
unsigned int getSize();
unsigned int getMaxCapacity();
T* getData();
};
template <class T>
double ABS<T>::scale = 2.0;
template <class T>
ABS<T>::ABS()
{
capacity = 1;
size =0;
data = new T[capacity];
}
template <class T>
ABS<T>::ABS(int capacity)
{
this->capacity = capacity;
size = 0;
data = new T[this->capacity];
}
template <class T>
ABS<T>::ABS(const ABS<T> &d)
{
capacity = d.capacity;
size = d.size;
data = new T[capacity];
for(int i=0;i<size;i++)
data[i] = d.data[i];
}
template <class T>
ABS<T>& ABS<T> ::operator=(const ABS<T> &d)
{
if(this != &d)
{
delete [] data;
capacity = d.capacity;
size = d.size;
data = new T[capacity];
for(int i=0;i<size;i++)
data[i] = d.data[i];
}
return *this;
}
template <class T>
ABS<T>::~ABS()
{
delete [] data;
}
template <class T>
void ABS<T>:: push(T data)
{
if(size == capacity)
{
resize(scale);
}
this->data[size] = data;
size++;
}
template <class T>
T ABS<T>::pop()
{
if(size == 0)
throw runtime_error("Cannot pop from an empty stack");
T item = data[size-1];
size--;
if(capacity > 1)
{
if((((double)size)/capacity) < ((double)1/scale))
resize((double)1/scale);
}
return item;
}
template <class T>
T ABS<T>::peek()
{
if(size == 0)
throw runtime_error("Cannot peek from an empty stack");
T item = data[size-1];
return item;
}
template <class T>
unsigned int ABS<T>:: getSize()
{
return size;
}
template <class T>
unsigned int ABS<T>::getMaxCapacity()
{
return capacity;
}
template <class T>
T* ABS<T>::getData()
{
return data;
}
template <class T>
void ABS<T>::resize(double scale)
{
T *tempData = new T[(int)(capacity*scale)];
for(int i=0;i<size;i++)
tempData[i] = data[i];
capacity = capacity*scale;
delete [] data;
data = tempData;
}
//end of ABS
template <class T>
class ABQ
{
static double scale;
unsigned int size;
unsigned int capacity;
T *data;
void resize(double scale);
public:
ABQ();
ABQ(int capacity);
ABQ(const ABQ &d) ;
ABQ& operator=(const ABQ &d);
~ABQ() ;
void enqueue(T data);
T dequeue();
T peek() ;
unsigned int getSize();
unsigned int getMaxCapacity();
T* getData();
};
template <class T>
double ABQ<T>::scale = 2.0;
template <class T>
ABQ<T>::ABQ()
{
capacity = 1;
size = 0;
data = new T[capacity];
}
template <class T>
ABQ<T>::ABQ(int capacity)
{
this->capacity = capacity;
size = 0;
data = new T[this->capacity];
}
template <class T>
ABQ<T>::ABQ(const ABQ<T> &d)
{
capacity = d.capacity;
size = d.size;
data = new T[capacity];
for(int i=0;i<size;i++)
data[i] = d.data[i];
}
template <class T>
ABQ<T>& ABQ<T>::operator=(const ABQ<T> &d)
{
if(this != &d)
{
delete [] data;
capacity = d.capacity;
size = d.size;
data = new T[capacity];
for(int i=0;i<size;i++)
data[i] = d.data[i];
}
return *this;
}
template <class T>
ABQ<T>::~ABQ()
{
delete [] data;
}
template <class T>
void ABQ<T>:: enqueue(T data)
{
if(size == capacity)
{
resize(scale);
}
this->data[size] = data;
size++;
}
template <class T>
T ABQ<T>::dequeue()
{
if(size == 0)
throw runtime_error("Cannot dequeue from an empty queue");
T item = data[0];
for(int i=0;i<size-1;i++)
data[i] = data[i+1];
size--;
if(capacity > 1)
{
if((((double)size)/capacity) < ((double)1/scale))
resize((double)1/scale);
}
return item;
}
template <class T>
T ABQ<T>::peek()
{
if(size == 0)
throw runtime_error("Cannot dequeue from an empty queue");
return data[0];
}
template <class T>
unsigned int ABQ<T>:: getSize()
{
return size;
}
template <class T>
unsigned int ABQ<T>::getMaxCapacity()
{
return capacity;
}
template <class T>
T* ABQ<T>::getData()
{
return data;
}
template <class T>
void ABQ<T>::resize(double scale)
{
T *tempData = new T[(int)(capacity*scale)];
for(int i=0;i<size;i++)
tempData[i] = data[i];
capacity = capacity*scale;
delete [] data;
data = tempData;
}
//end of ABQ
Lab 3 – Array-Based Stack and Queue Overview In this assignment, you will be implementing your...
C++ Create an array-based implementation of a stack. Each element of the stack should store a string. The stack class should include 3 private member variables (maximum stack size, top of the stack index, and a pointer to the array that holds the stack elements). Public member methods should include a constructor (with an argument of stack maximum size that is used to create a dynamic array), a destructor (that deletes the dynamic array), a push method (argument is a...
1. Here are codes to define a stack class based on dynamic array, please complete the copy constructor //--- Definition of Stack copy constructor Stack::Stack(const Stack & original) : myCapacity(original.myCapacity), myTop(original.myTop) { //--- Get new array for copy myArray = new(nothrow) StackElement[myCapacity]; if (myArray != 0) // check if memory available // copy original's array member into this new array { // Please complete the function here } else { cerr << "*Inadequate memory to allocate...
5. Stack (12 pts) Build a Stack class for a st The Stack should operat and methods also listed below ack of doubles that is compatible with the driver code below e in a LIFO (last in, first out) fashion and implement the variables a. Data Members: Declare the data item(s) you will need to manage a stack of doubles. Method Members: public void push (double input): This should add the double input to your stack public double pop ():...
I need to implement a stack array but the top of the stack has to be Initialize as the index of the last location in the array. //Array implementation of stacks. import java.util.Arrays; public class ArrayStack implements Stack { //Declare a class constant called DEFAULT_STACK_SIZE with the value 10. private static final int DEFAULT_STACK_SIZE = 10; /* Declare two instance variables: 1. An integer called...
QUESTION: ADT stack: resizable array-based implementation for Ch4 programming problem 4 "maintain the stacks's top entry at the end of the array" at array index N-1 where the array is currently allocated to hold up to N entries. MAKE SURE YOU IMPLEMENT the functions: bool isEmpty() const; bool push(const ItemType& newEntry); bool pop(); in ArrayStackP4.cpp //FILE StackInterface.h #ifndef STACK_INTERFACE_ #define STACK_INTERFACE_ template<class ItemType> class StackInterface { public: /** Sees whether this stack is empty. @return True if the...
In c++ Section 1. Stack ADT – Overview Data Items The data items in a stack are of generic DataType. This means use should use templating and your Node class. Structure The stack data items are linearly ordered from the most recently added (the top) to the least recently added (the bottom). This is a LIFO scheme. Data items are inserted onto (pushed) and removed from (popped) the top of the stack. Operations Constructor. Creates an empty stack. Copy constructor....
Review the Stack implementation with Vector, and implement/answer the following methods. Stack One of the principles of good programming is to reuse existing code whenever practical. If you can reuse existing code, you don't need to spend the time to rewrite it. Code used previously has also been debugged, and will likely contain fewer errors. One of the easiest ways to create a container is to leverage an existing data type to build a new abstraction. In this lesson we...
Java - data structures Suppose that in the array-based stack, the array doubles in size after multiple push operations. But later on, fewer than half of the array’s locations might actually be used by the stack due to pop operations. Revise the implementation so that its array also can shrink in size as objects are removed from the stack. Accomplishing this task will require two new private methods, as follows: The first new method checks whether we should reduce the...
Given an array-based stack of integers, sort it largest to smallest using recursion. Do NOT use any loop constructs such as while, for and so on. Only use the following stack ADT functions in the recursion: IsEmpty Push Pop Top (note: doesn’t remove anything from the stack). Your program should read 10 integers into a stack from a file named input.txt (outputting them to the screen first) then implement the recursions. Use stacks only, no queues. The program should then...
In Java language: 1. The complement of a queue is a stack. It uses first-in, last-out accessing and is often likened to a stack of plates. The first plate put on the table is the last plate used. Create a stack class called Stack that can hold characters. Call the methods that access the stack push( ) and pop( ). Allow the user to specify the size of the stack when it is created. Keep all other members of the...