数据结构——栈(数组描述)

栈是一种常用的数据结构。栈这种数据结构可以通过数组或链表两种方式进行描述,因为栈的特点,所以数组是栈的常用表现形式,本文主要介绍了栈的数组形式,并通过数制之间转换的例子介绍了栈的建立、入栈和出栈等基本操作。

1 栈
把线性表的插入和删除操作放在同一端进行,就得到了栈数据结构,它是一种后进先出(last in first out)的数据结构。栈是一种特殊的线性表,其插入(入栈/压栈)和删除(出栈/弹栈)操作都在表的同一端进行。这一端称为栈顶,另一端称为栈底。打印机托盘上的打印纸的使用情况就可以看作是一种栈的操作。
栈的数组描述的抽象数据类型如下:

class Stack
{  public:
    Stack(int size);    //初始化栈,包括栈的大小,栈顶标记
    char pop();         //出栈
void push(char e);  //入栈,栈的大小不够时,动态增加栈的大小
void empty()        //栈是否为空 
    char* stack;        //用数组表示栈,栈的数组描述
private:
    int size;         //栈的大小
    int top;          //栈顶标记
};

利用数组对栈进行描述,这种抽象数据类型包括了基本的栈初始化、入栈、出栈等操作和栈顶、栈的大小的标记。由于数据保护,这里将栈顶和栈的大小定义为private变量,如果需要此变量,可以新增public函数gettop()函数返回栈顶。

2 实例
栈的操作中,最重要个常用的就是入栈和出栈操作。下面用实例进行说明。
1. 这是一个简单的栈的建立、入栈和出栈的例子。通过这个例子熟悉栈的数组描述形式。
//栈的数组描述,(进栈、出栈和动态增加栈的长度)

#include<iostream>
#include<cmath>
using namespace std;
class Stack
{
public:
    Stack(int initialCapacity=10)        //构造函数
    {
        size=initialCapacity;
        stack= new char[size];
        top=-1;
    }
    void push(char element);       //进栈
// char pop(char* element); //出栈 通过指针,指向出栈的元素
/*char Stack::pop(char* element) { element=&stack[top--]; return *element; } */
    char pop()                         //出栈 直接返回出栈的元素
    {
        if(top==-1)
        {
            cout<<"栈已经为空!"<<endl;
            exit(0);
        }
        return stack[top--];
    } 
    int top;                             //当前栈顶
    int size;                            //栈的容量
    char* stack;                         //元素数组
};
//动态增加栈的大小
void Stack::push(char element)
{
    if(top==size-1)
    {   
        size*=2;
        char* p=new char[size];
        for(int i=0;i<=top;i++)
            p[i]=stack[i];
        delete[] stack;
        stack=p;
    }
    stack[++top]=element;
}

int main()
{
    Stack stack; 
    for(int i=0;i<stack.size;i++)         //10个元素进栈
        stack.push('a'+i);
    for( i=0;i<20;i++)   //20个元素出栈,栈为空时退出。可以修改i的循环范围看变化
        cout<<stack.pop()<<endl;
    return 0;
}
  1. 数的进制之间的相互转化
    //栈的数组描述,二进制转换为十进制和八进制数
    //栈用数组描述时,最少需要一个数组变量(指针)作为栈stack,栈顶标记top,和栈的大小size
#include<iostream>
#include<cmath>
using namespace std;

class Stack
{
public:
    Stack(int size)        //初始化栈,包括栈的大小,栈顶标记
    {
        this->size=size;    //实参和形参都取名为size,所以用this指针区别
        stack=new char[this->size]; 
        top=-1;
    }

    char pop()                    //出栈
    {
        if(top==-1)
        {
            cout<<"栈已为空!"<<endl;
            exit(0);
        }
        return stack[top--];    
    }

void push(char e)      //入栈,栈的大小不够时,动态增加栈的大小
    {
        if(top==size-1)
        {       
            size=size+10;
            char*p=new char[size];
            for(int i=0;i<size;i++)
                p[i]=stack[i];
            delete[] stack;
            stack=p;
        }
        stack[++top]=e;
    }

private:
    int size;         //栈的大小
    int top;          //栈顶标记
    char* stack;      //用数组表示栈,栈的数组描述

};

int main()
{
    Stack s(5);                     //初始化栈,大小为5,用于二进制数
    int o[20];                     //用于记录八进制数

    char binary[100];              //二进制数用字符数组表示
    cout<<"Please input the binary number:"<<" ";
    cin>>binary;
// cout<<binary;

//**************二进制数转换
    int len=strlen(binary);            //求二进制数的位数
// cout<<len<<endl;

    for(int i=0;i<len;i++)      //将二进制数入栈,入栈和数组都从0开始
        s.push(binary[i]);  

    int sum=0;
    for( i=0;i<len;i++)       //出栈并计算
        sum=sum+int(s.pop()-'0')*pow(2,i);
    cout<<"The decimal number is: "<<sum<<endl; 

    for( i=0;i<len;i++)   //因为前面已出栈,所以这里将二进制数再次入栈
        s.push(binary[i]);  

//*************八进制数转换
    int k=0;                   //数组下标
    for( i=0;i<len;)                    //出栈并计算
    {   
        int temp=0;
        for(int j=0;j<3&&i<len;j++)
        {
            temp=temp+int(s.pop()-'0')*pow(2,j);
            i++;
        }
        //cout<<temp<<endl;
        o[k++]=temp;        //将计算的八进制数放入数组
    }

    cout<<"The octal number is: "; 
    for(i=k-1;i>=0;i--)     //反向输出数组
        cout<<o[i];

    cout<<endl;
    return 0;
}

你可能感兴趣的:(数据结构,栈,进制转换,数组描述,入栈出栈)