/* Copyright (c) 1993 by Sanjay Ghemawat */
#ifndef _STACK_H
#define _STACK_H

#include <generic.h>
#include "Array.h"

#define StackArray(StackType) name2(StackType,_Array)

#define declareStack(StackType,ElementType)				      \
declareArray(StackArray(StackType),ElementType)				      \
									      \
class StackType {							      \
  public:								      \
    StackType();							      \
    /* EFFECTS: Returns a new empty stack */				      \
									      \
    ~StackType();							      \
    /* EFFECTS: Destroys THIS */					      \
									      \
    int empty() const;							      \
    /* EFFECTS: Returns true iff THIS is not empty */			      \
    									      \
    ElementType top() const;						      \
    /* REQUIRES: THIS is not empty. */					      \
    /* EFFECTS:  Returns top element from THIS. */			      \
									      \
    ElementType pop();							      \
    /* REQUIRES: THIS is not empty. */					      \
    /* EFFECTS:  Removes and returns top element from THIS. */		      \
									      \
    void push(ElementType);						      \
    /* MODIFIES: THIS */						      \
    /* EFFECTS:  Pushes element onto THIS */				      \
  private:								      \
    StackArray(StackType) list;						      \
};									      \
									      \
inline StackType::StackType() : list() { }				      \
inline StackType::~StackType() { }					      \
									      \
inline int StackType::empty() const {					      \
    return (list.size() == 0);						      \
}									      \
									      \
inline ElementType StackType::top() const {				      \
    return (list.high());						      \
}									      \
									      \
inline ElementType StackType::pop() {					      \
    return (list.remove());						      \
}									      \
									      \
inline void StackType::push(ElementType e) {				      \
    list.append(e);							      \
}									      \

#define implementStack(StackType,ElementType)				      \
implementArray(StackArray(StackType),ElementType)			      \

#endif /* _STACK_H */
