前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布

作者头像
青木
发布2018-08-15 15:17:20
4060
发布2018-08-15 15:17:20
举报

定义和应用

(stack)是一种特殊的线性表,其插入(也称入栈或压栈)和删除(也称出栈或弹栈)操作都在表的同一端进行。这一端被称为栈顶top)另一端称为栈底端bottom)。 我们生活中其实有很多东西都用到了栈的原理。

  • 打印机。打印纸托盘其实就是一个栈。放在最上面的纸会优先被使用,而实际上放在下面纸才是首先放进托盘的。
  • 盘子。每天在食堂吃饭的时候,大家会从一摞盘子上取一个盛放食物,最上面的盘子会被优先拿走,实际上最下面的盘子是优先被食堂阿姨放好的。
  • 书店买书。我们买书的时候,都是从最上面取走一本。 计算机中有一个东西也用了栈的思想:递归。 计算机使用递归工作栈来执行递归函数。 下面是栈的实现代码:
代码语言:javascript
复制
/*
 * 栈测试代码
 arrayStack.cpp
*/
#include<iostream>
#include"arraystack.h"
#include"myexceptions.h"

using namespace std;
int main(void)
{
    arrayStack<int> s;

    s.push(1);
    s.push(2);
    s.push(3);
    s.push(4);

    cout <<"Stack should be 1234,bottom to top"<<endl;

    if(s.empty())
        cout<<"The stack is empty"<<endl;
    else
        cout <<"The stack is not empty"<<endl;

    cout <<"The stack size is "<<s.size()<<endl;

    while(!s.empty())
    {
        cout <<"Stack top is "<<s.top()<<endl;
        s.pop();
        cout<<"Popped top element"<<endl;
    }

    try{s.pop();}
    catch(stackEmpty message)
    {
        cout <<"Last pop failed"<<endl;
        message.outputMessage();
    }

    return 0;
}
代码语言:javascript
复制
/*栈操作的头文件
 * 规定了栈操作的可能使用函数
 * stack.h
*/
#ifndef STACK_H
#define STACK_H

using namespace std;

template<class T>
class stack
{
public:
    virtual ~stack(){}

    //判断是否空栈
    virtual bool empty()const = 0;

    //返回栈空间中元素数量
    virtual int size() const = 0;

    //返回栈顶元素的索引
    virtual T& top() = 0;

    //出栈操作
    virtual void pop() = 0;

    //入栈操作
    virtual void push(const T& theElement) = 0;
};


#endif // STACK_H
代码语言:javascript
复制
/*
 * 对抽象类stack的具体实现
 * arrayStack.h
*/

#ifndef ARRAYSTACK_H
#define ARRAYSTACK_H

#include"stack.h"
#include"myexceptions.h"
#include"changelength1d.h"
#include<sstream>

template<class T>
class arrayStack : public stack<T>
{
  public:
    arrayStack(int initialCapacity = 10);
    ~arrayStack(){delete [] stack;}

    bool empty() const{return stackTop == -1;}
    int size() const
    {
        return stackTop + 1;
    }
    T& top()
    {
        if(stackTop == -1)
            throw stackEmpty();
        return stack[stackTop];
    }
    void pop()
    {
        if(stackTop == -1)
            throw stackEmpty();
        stack[stackTop--].~T();
    }
    void push(const T &theElement);
private:
    int stackTop;
    int arrayLength;
    T *stack;
};

template<class T>
arrayStack<T>::arrayStack(int initialCapacity)
{
    if(initialCapacity < 1)
    {
        ostringstream s;
        s <<"Initial capacity = "<<initialCapacity
         <<"Must be > 0";
        throw illegalParameterValue(s.str());
    }
    arrayLength = initialCapacity;
    stack = new T[arrayLength];
    stackTop = -1;
}

template<class T>
void arrayStack<T>::push(const T &theElement)
{
    if(stackTop == arrayLength - 1)
    {
        changeLength1D(stack,arrayLength,arrayLength*2);
        arrayLength *= 2;
    }
    stack[++stackTop] = theElement;
}


#endif // ARRAYSTACK_H
代码语言:javascript
复制
/*
 * 变长数组:1维
 * changeLength1D.h
*/
#ifndef CHANGELENGTH1D_H
#define CHANGELENGTH1D_H

#include"myexceptions.h"

using namespace std;

int min(int a,int b)
{
    return (a >= b)?b:a;
}

template<class T>
void changeLength1D(T*& a,int oldLength,int newLength)
{
    if(newLength < 0)
        throw illegalParameterValue("new length must be >= 0");

    T* temp = new T[newLength];
    int number = min(oldLength,newLength);
    copy(a,a+number,temp);
    delete [] a;
    a = temp;
}

#endif // CHANGELENGTH1D_H
代码语言:javascript
复制
/*
 * 栈操作的异常处理类
 * myExceptions.h
*/
#ifndef MYEXCEPTIONS_H
#define MYEXCEPTIONS_H

#include<string>

using namespace std;


//参数不合法异常
class illegalParameterValue
{
public:
    illegalParameterValue(string theMessage =
            "Illegal parameter value")
    {
        message = theMessage;
       // 10.95.251.52
    }
    void outputMessage()
    {
        cout <<message<<endl;
    }
private:
    string message;
};


//栈空异常
class stackEmpty
{
public:
    stackEmpty(string theMessage =
            "Invalid operation on empty stack")
    {
        message = theMessage;
    }
    void outputMessage()
    {
        cout <<message <<endl;
    }
private:
    string message;
};

#endif // MYEXCEPTIONS_H
本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 定义和应用
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档