栈的基本操作
栈是一种限制插入和删除操作只能在一个位置上进行的表,那个位置在栈顶。也被称为后进先出(Last In-First Out)表。栈的应用非常广泛。只要满足后进先出的特性就可以利用。比如判断符号是否成对出现、计算机中计算后缀表达式的值、中缀表达式转换为后缀表达式,以及多个经典算法中对于路径的搜索实现路径的保存等。其中,栈的一个最重要的应用,也是最经常使用的应用,就是对函数的调用。
栈的结构,如图所示:
对于栈的基本操作,具体要做些什么?
1.将数据压入Stack
2.将数据从Stack弹出
3.判断此Stack是否为空
4.返回此Stack元素个数
5.返回此Stack顶端元素
6.对空栈企图进行弹出元素和返回顶端元素的情况,进行异常处理
通过观察STL源码,进而学习世界一流程序员的身手、组合成自己的代码、进一步提升STL扩充能力,是一种相当合适的方式。
下面上传部分STL源代码截图~~
选自<stack> ,说明实作在stl_stack.h中,默认用deque作为底层容器
选自stl_stack.h,对底层容器及对应类型进行了命名,容器默认为deque.
由于deque是双向开口的数据结构,若以deque为底部结构并封闭头端开口,便轻而易举地形成了一个stack。
并且,list也是双向开口的数据结构,而且deque所选用的函数,list都具备。所以,用list作为底部容器也是一个不错的选择。
选自stl_stack.h,这里对empty(),size()和top()进行了定义
选自stl_stack.h,这里对push()进行了定义
选自stl_stack.h,这里对pop()进行了定义
最后通过以上STL源代码以及部分参考文献,表达出自己的代码:
// Stack.hpp
#ifndef STACK_HPP
#define STACK_HPP
#include<iostream>
#include<deque>
#include<list>
#include<exception>
template<typename T>
class Stack
{
private:
std::deque<T> c; //由于Stack的内部结构和deque以及list很相似 也可以std::list<T> c;
public:
class ReadEmptyStack :public std::exception
{
public:
virtual const char* what()const throw()
{
return "the Stack is empty";
}
};
bool empty()const {return c.empty(); } //判断栈是否为空
typename std::deque<T>::size_type size()const {return c.size(); } //返回容器元素个数
T& top() //返回栈顶元素
{
if (empty())
throw ReadEmptyStack();
T& top(c.back());
return top;
}
void push(const T& element) //将元素压入栈中
{
c.push_back(element);
}
bool pop() //将元素从栈中
{
if (empty())
{
throw ReadEmptyStack();
return false;
}
c.pop_back();
return true;
}
};
#endif
参考文献:
1.《C++标准模板库 -自修教程及参考手册-》 Nicolai M.Josuttis著,侯捷/孟岩译
2.《STL源码剖析》 侯捷著
3.《数据结构与算法分析 C++描述》 第3版 Mark Allen Weiss著,张怀勇等译