参考链接:数据结构探险—栈篇

学了队列之后,栈就很简单了,换汤不换药。

 


栈的模型

后进先出(电梯,进制转换,括号的匹配检测)

 

栈的基本元素

栈顶,栈底(一般很少用到),栈容量,栈长度

注意:栈顶一般指向栈最后一个元素的下一位

 

标准C++代码

//MyStack.h
#pragma once
class MyStack
{
public:
    MyStack(int size);
    ~MyStack();
    bool stackEmpty();
    bool stackFull();
    void clearStack();
    int stackLength();
    bool push(char elem);
    bool pop(char &elem);
    void stackTraverse();
private:
    char *m_pBuffer;
    int m_iSize;
    int m_iTop;
};
//MyStack.cpp
#include"MyStack.h"
#include<iostream>
using namespace std;

MyStack::MyStack(int size)
{
    m_iSize = size;
    m_pBuffer = new char[size];
    m_iTop = 0;
}

MyStack::~MyStack()
{
    delete[]m_pBuffer;
}

bool MyStack::stackEmpty()
{
    if (0 == m_iTop)
    {
        return true;
    }
    return false;
}

bool MyStack::stackFull()
{
    if (m_iTop == m_iSize)
    {
        return true;
    }
    return false;
}

void MyStack::clearStack()
{
    m_iTop = 0;
}

int MyStack::stackLength()
{
    return m_iTop;
}

bool MyStack::push(char elem)
{
    if (stackFull())
    {
        return false;
    }
    m_pBuffer[m_iTop] = elem;
    m_iTop++;
    return true;
}

bool MyStack::pop(char &elem)
{
    if (stackEmpty())
    {
        return false;
    }
    m_iTop--;
    elem = m_pBuffer[m_iTop];
    return true;

}

void MyStack::stackTraverse()
{
    for (int i = 0; i < m_iTop; i++)
    {
        cout << m_pBuffer[i] << ",";
    }
}
//demo.cpp
#include<iostream>
#include"MyStack.h"
using namespace std;

int main()
{
    MyStack *p = new MyStack(5);

    p->push('h');
    p->push('e');
    p->push('l');
    p->push('i');
    p->push('z');

    p->stackTraverse();

    char tmp = 0;
    p->pop(tmp);
    cout << endl << "ding is " << tmp << endl;

    p->clearStack();

    cout << p->stackLength() << endl;

    if (p->stackEmpty())
    {
        cout << "stack is empty" << endl;
    }
    if (p->stackFull())
    {
        cout << "stack is full" << endl;
    }
    delete p;
    p = nullptr;
    return 0;
}

改变栈元素的类型

#pragma once

class Coordinate
{
public:
    Coordinate(int x = 0, int y = 0);
    void printCoordinate();
private:
    int m_iX;
    int m_iY;
};
#include"Coordinate.h"
#include<iostream>
using namespace std;

Coordinate::Coordinate(int x, int y)
{
    m_iX = x;
    m_iY = y;
}

void Coordinate::printCoordinate()
{
    cout << "(" << m_iX << "," << m_iY << ")" << endl;
}
#include<iostream>
#include"MyStack.h"
using namespace std;

/******************************************/
/*
栈类
要求:
    1.定义Coordinate坐标类
    2.改造栈类,使其可以适用于坐标类
目的:灵活掌握栈机制,理解抽象数据类型在栈中的应用
*/
/******************************************/

int main()
{
    MyStack *p = new MyStack(5);

    p->push(Coordinate(1,2));
    p->push(Coordinate(3,4));

    p->stackTraverse();

    Coordinate tmp = 0;
    p->pop(tmp);
    cout << endl << "tmp is ";
    tmp.printCoordinate();

    p->clearStack();

    cout << "Length: " << p->stackLength() << endl;

    if (p->stackEmpty())
    {
        cout << "empty" << endl;
    }
    if (p->stackFull())
    {
        cout << "full" << endl;
    }

    delete p;
    p = nullptr;
    return 0;
}

类模板重写栈

#pragma once
#include<ostream>
using namespace std;

class Coordinate
{
    friend ostream &operator<<(ostream &out, Coordinate &coor);
public:
    Coordinate(int x = 0, int y = 0);
    void printCoordinate();
private:
    int m_iX;
    int m_iY;
};
#include"Coordinate.h"
#include<iostream>
using namespace std;

Coordinate::Coordinate(int x, int y)
{
    m_iX = x;
    m_iY = y;
}

void Coordinate::printCoordinate()
{
    cout << "(" << m_iX << "," << m_iY << ")" << endl;
}

ostream &operator<<(ostream &out, Coordinate &coor)
{
    out << "(" << coor.m_iX << "," << coor.m_iY << ")" << endl;
    return out;
}
#pragma once

template <typename T>
class MyStack
{
public:
    MyStack(int size);    //分配内存初始化栈空间,设定 栈容量,栈顶
    ~MyStack();    //回收栈空间内存
    bool stackEmpty();    //判定栈是否为空,为空返回true,非空返回false
    bool stackFull();    //判定栈是否为满,为满返回true,不满返回false
    void clearStack();    //清空栈
    int stackLength();    //已有元素的个数
    bool push(T elem);    //元素入栈,栈顶上升
    bool pop(T &elem);    //元素出栈,栈顶下降
    void stackTraverse();    //遍历栈中所有元素
private:
    T *m_pBuffer;//栈空间指针
    int m_iSize;    //栈容量
    int m_iTop;        //栈顶,栈中元素个数
};

//不支持分开编译
template <typename T>
MyStack<T>::MyStack(int size)    //分配内存初始化栈空间,设定 栈容量,栈顶
{
    m_iSize = size;
    m_pBuffer = new T[size];
    m_iTop = 0;
}

template <typename T>
MyStack<T>::~MyStack()    //回收栈空间内存
{
    delete[]m_pBuffer;
    m_pBuffer = nullptr;
}

template <typename T>
bool MyStack<T>::stackEmpty()//判定栈是否为空,为空返回true,非空返回false
{
    if (0 == m_iTop)
    {
        return true;
    }
    return false;
}

template <typename T>
bool MyStack<T>::stackFull()    //判定栈是否为满,为满返回true,不满返回false
{
    if (m_iTop == m_iSize)
    {
        return true;
    }
    return false;
}

template <typename T>
void MyStack<T>::clearStack()    //清空栈
{
    m_iTop = 0;
}

template <typename T>
int MyStack<T>::stackLength()    //已有元素的个数
{
    return m_iTop;
}

template <typename T>
bool MyStack<T>::push(T elem)    //元素入栈,栈顶上升
{
    if (stackFull())
    {
        return false;
    }
    m_pBuffer[m_iTop] = elem;
    m_iTop++;
    return true;
}

template <typename T>
bool MyStack<T>::pop(T &elem)    //元素出栈,栈顶下降
{
    if (stackEmpty())
    {
        return false;
    }
    m_iTop--;
    elem = m_pBuffer[m_iTop];
    return true;
}

template <typename T>
void MyStack<T>::stackTraverse()    //遍历栈中所有元素
{
    for (int i = 0; i < m_iTop; i++)
    {
        //m_pBuffer[i].printCoordinate();//可以使用运算符重载
        cout << m_pBuffer[i];
    }
}
#include<iostream>
#include"MyStack.h"
using namespace std;
#include"Coordinate.h"

/******************************************/
/*
栈 类模板
要求:
    将普通栈改造为类模板栈,使其可以适用于任何数据类型
目的:灵活掌握栈机制,理解抽象数据类型在栈中的应用
*/
/******************************************/

int main()
{
    MyStack<Coordinate> *p = new MyStack<Coordinate>(5);

    p->push(Coordinate(1,2));
    p->push(Coordinate(3,4));

    p->stackTraverse();

    Coordinate tmp = 0;
    p->pop(tmp);
    cout << endl << "tmp is ";
    tmp.printCoordinate();

    p->clearStack();

    cout << "Length: " << p->stackLength() << endl;

    if (p->stackEmpty())
    {
        cout << "empty" << endl;
    }
    if (p->stackFull())
    {
        cout << "full" << endl;
    }

    delete p;
    p = nullptr;
    return 0;
}

 

实际应用一:进制转换

 

 

 

实例应用二:括号匹配