#include <iostream>
using namespace std;
template <typename T>
class pushOnFull {
T _value;
public:
pushOnFull(T i) {
_value = i;
}
T value() {
return _value;
}
void print() {
cout << "Stack is full," << _value << " is not pushed" << endl;
}
};
template<typename T>
class popOnEmpty {
public:
void print() {
cout << "stack is empty, can't pop" << endl;
}
};
template<typename T>
class Stack{
int top;
T *elements;
int maxSize;
public:
Stack(int = 20) ;
~Stack() {
delete[] elements;
}
void Push(const T & data);
T Pop();
T GetEle(int i) {
return elements[i];
}
void makeEmpty() {
top = -1;
}
bool isEmpty() const {
return top == -1;
}
bool isFull() const {
return top == maxSize-1;
}
void printStack();
};
template<typename T>
Stack<T>::Stack(int maxs) {
maxSize = maxs;
top = -1;
elements = new T[maxSize];
}
template<typename T>
void Stack<T>::printStack() {
for(int i = 0; i < top; i++) {
cout << elements[i] << " ";
}
cout << endl;
}
template<typename T>
void Stack<T>::Push(const T &data) {
if(isFull()) {
throw pushOnFull<T>(data);
}
elements[++top] = data;
}
template<typename T>
T Stack<T>::Pop() {
if(isEmpty()){
throw popOnEmpty<T>();
}
return elements[top--];
}
int main()
{
int a[9] = {1, 8, 7, 6, 5, 4, 3, 2, 1}, b[9] = {0}, i;
Stack<int> istack(8);
try {
for(int i = 0; i < 9; i++)
istack.Push(a[i]);
istack.printStack();
}
catch(pushOnFull<int> & eobj) {
eobj.print();
}
try{
for(int i = 0; i < 9; i++)
b[i] = istack.Pop();
istack.printStack();
}
catch(popOnEmpty<int> & eobj) {
eobj.print();
}
cout << "Pop order is:";
for(int i = 0; i < 9; i++)
cout << b[i] << " ";
cout << endl;
return 0;
}