This article implements most of the stack functions in STL and adds some features.
Note the following:
1. Stack is an adapter. The underlying layer is implemented by vector, list, And deque.
2. The stack does not contain an iterator
In this example, I have added several features, including copying and assigning values between different types of stacks, which can implement stack <int, vector <int> and stack <double, list <double> is mainly implemented by the member function template.
To implement the above functions more conveniently, I added a function:
const_container_reference get_container() const
To obtain the reference of the internal container.
In addition, the stack of the standard library does not check out-of-bounds behaviors. I added Exception Handling for the stack. When the stack is empty, executing pop or top will throw an exception. This exception class inherits from exception (see the previous article) and is used to indicate stack null.
The detailed code is as follows: for exception implementation, see: exception class exception with backtrace and demangle.
# Ifndef stack_hpp _ # define stack_hpp _ # include "exception. H "# include <deque> // class emptystackexception: Public exception {public: emptystackexception (): exception (" read empty stack "){}}; template <typename T, typename Container = STD: deque <t> class Stack {public: typedef t value_type; typedef T & reference; typedef const T & const_reference; typedef container container_type; // container type typedef emptystackexception exception_type; // exception type typedef typename container: size_type; typedef container & container_reference; // container reference typedef const container & const_container_reference; explicit stack (const container_type & Cont = container_type (): cont _ (cont ){}
// Copy template <typename T2, typename container2> stack <t, container> (const stack <t2, container2> & S) between different types ); // set the value of template <typename T2, typename container2> stack <t, container> & operator = (const stack <t2, container2> & S) for different types ); void push (const value_type & Val) {cont _. push_back (VAL);} void POP () {If (cont _. empty () Throw exception_type (); cont _. pop_back ();} reference top () {If (cont _. empty () Th Row exception_type (); Return cont _. back ();} const_reference top () const {If (cont _. empty () Throw exception_type (); Return cont _. back ();} bool empty () const {return cont _. empty ();} size_type size () const {return cont _. size () ;}// obtain the reference const_container_reference get_container () const {return cont _;} friend bool operator ==( const stack & A, const stack & B) of the internal container) {return. cont _ = B. cont _;} Fri End bool Operator! = (Const stack & A, const stack & B) {return a. cont _! = B. cont _;} friend bool operator <(const stack & A, const stack & B) {return. cont _ <B. cont _;} friend bool operator> (const stack & A, const stack & B) {return. cont _> B. cont _;} friend bool operator <= (const stack & A, const stack & B) {return. cont _ <= B. cont _;} friend bool operator >=( const stack & A, const stack & B) {return. cont _> = B. cont _;} private: Container cont _;}; Template <typename t, Typename container> template <typename T2, typename container2> stack <t, container>: Stack (const stack <t2, container2> & S): cont _ (s. get_container (). begin (), S. get_container (). end () {} template <typename T, typename container> template <typename T2, typename container2> stack <t, container> & stack <t, container> :: operator = (const stack <t2, container2> & S) {If (void *) This! = (Void *) & S) {cont _. assign (S. get_container (). begin (), S. get_container (). end ();} return * This;} # endif/* stack_hpp _*/
The test code is as follows:
# Include "stack. HPP "# include <iostream> # include <string> # include <vector> # include <list> # include <stdio. h> using namespace STD; int main (INT argc, char const * argv []) {try {stack <string, vector <string> st; ST. push ("foo"); ST. push ("bar"); stack <string, list <string> st2 (ST); // st2 = sT; while (! St2.empty () {cout <st2.top () <Endl; st2.pop () ;}st2.pop (); // raises an exception} catch (const exception & Ex) {fprintf (stderr, "Reason: % s \ n", Ex. what (); fprintf (stderr, "stack trace: % s \ n", Ex. stacktrace ();} return 0 ;}
An implementation of standard library stack