栈的应用举例

栈和队列主要用于计算过程中保存的临时数据,如果数据在编程时就可以确定,那么使用几个变量就可以临时存储,但是如果存储的数据项数不能确定,就需要复杂的存储机制。这样的存储机制称为缓存。栈和队列就是使用最多的缓存结构。


我们在调用方法的时候 , 时常调用别的成员方法, 递归循环调用 , 那调用到最后,又从最后一个函数,依次返回值 , 我们熟悉这个机制.

但是我们却不知道 , 编译器是如何把这些调用信息存储起来的,用什么方法存储起来的, 这里就需要我们用到栈了,先进后出 

还有生活中 , 我们往木桶里放球 ,


先放进去的后拿出来 ,我们只能在一端进行操作 

还有当我们在车站的栈道里面 

 

 先进来的车 ,因为后进来的还有车 , 后进来的车堵住了去路 , 所以 后进来的车可以先出 

以上的例子 , 只是生活中的一些情况 , 我们还会遇到很多类似的模型 , 那用什么来记录这些模型信息呢? 

先分析元素进入的特点 , 我们只是在容器的一段进行操作 , 并且操作的总是顶端的那个元素 

然后后进来的元素 ,因为离出口近 ,可以先出去

由此我们可以构建一个栈道模型 , 简称栈 

操作的话, 我们只操作栈顶的元素 , 就用一个指针指栈顶元素.

所以,我们就可以定义栈的特有操作:


我们无非就是 , 定义了一个数组容器, 或者链表容器  , 然后用指针指向要操作的元素 ,就是所谓的栈顶  ,相应的栈底就是没有元素的时候 , 容器底部

元素进来 , 就把元素压入栈顶 , 指针指向栈顶 , 

元素出来 , 就把元素弹出栈顶 , 指针下移 ,移向栈顶

栈空间没有元素 , 就称作是空栈  , 就意味着不可以弹出元素

栈空间元素满了 , 就称作是满栈 , 就意味着不可以再压入元素


这就是把上述的语言描述,抽象了一下 ,作为彻底的唯物主义 , 我们还是直接上代码为妙 

构建栈的顺序存储结构

用顺序表来存储栈 ,需要指向栈顶的变量, 

由于顺序表是用数组来存储元素的,所以要求栈的数据元素需要同一类型 , 然后还要要固定的容量

●描述栈

        °数据元素: 元素具有同一类型 (ElemType) ,最多MaxSize

        °当前栈顶 : 记录栈顶的下标(栈顶指针)


typedef struct
{
    ElemType data[MaxSize];
    int top;
}SqStack;

注: 这里的 top 指向的是栈顶 , 就是数组里元素的最后一个数据元素 

 当我们定义的数组被元素填满的时候 ,  就栈满了

无元素的时候就代表 , 栈空

数组坐标是从 0开始的

下面我们开始构建顺序栈的操作条件:

●栈空条件: top = -1


栈空间有元素的时候 , 代表数组标号为 0 的位置上有元素 , top 指向数组坐标 0 的位置

,那栈空的时候 , top 就指向 -1 ,有元素的话,加一,正好变成 0 

 ●栈满条件: top = MaxSize - 1


数组坐标从 0 开始 , 所以top 指向的数组末尾元素的位序就是 MaxSize-1

●进栈操作 top++ ; 将 新节点放在 top 处


元素进栈前, 我们的栈顶指针 top 要向上移动 ,为元素腾空间 , 然后再放元素

●退栈操作 : 从top 处取出元素 ; 然后 top --


元素要出栈 ,所以要先从 top 指引处获得元素 ,然后把 top 处的元素删除 , top 下移

初始化栈 initStack(&s)

● 建立一个新的空栈 s ,实际上是将栈顶指针指向 -1 即可

void InitStack(SqStack *&s)
{
    s = (SqStack *)malloc(sizeof(SqStack));
    s->top = -1;
}

判断栈是否为空 StackEmpty(s)

●栈空的条件是 top 指向的是 -1 ,不指向 -1 就代表栈内有元素

bool StackEmpty(SqStack *s)
{
    return(s->top == -1);
}

销毁栈 ClearStack(&s)

● 释放栈 s 占用的存储空间

void DestroyStack(SqStack *&s)

{

        free(s);

}

因为顺序栈,实质就是一个数组 ,我们释放数组的空间, 就相当于销毁了栈

进栈Push(&s , e)

●条件: 在栈不满时 ,可以进栈

●操作:

        °将栈指针增 1

        °在该位置上插入新元素 e


传入 要进的栈 , 传入要插入的元素 e

bool Push (SqStack *&s ,ElemType e){

判断栈是否满栈

        

if(s->top == MaxSize-1)
{
       return false;
}

如果栈不满 ,就继续进行插入操作

//栈指针top自增1
s->top++;
//top指向要插入的元素
s->data[s->top] = e;
//表示插入成功,返回true
return true;
}

出栈 Pop(&s,&e)

条件: 栈不为空

操作:

        °将栈顶元素赋值给 e

        °将栈指针减一

//传入出栈的指针数组 和 弹出的元素指针
bool Pop(SqStack *&s,ElemType &e)
{
    //栈空的时候,栈顶指针指向 -1     
    if(s->top == -1)
    {
        //如果进入,就代表栈空,返回 false
        return false;
    }
    //不进入上面的话,就代表栈里有元素
    //把栈顶指针指向的元素,传出给指针e
    e = s -> data[s->top];
   //栈顶指针下移
    s -> top--;
    //弹出成功,返回true
    return true;
}

取栈顶元素 GetTop(s , e)

●条件: 栈不为空时

●操作: 将栈顶元素赋值给 e


和出栈的操作差不多 , 只是这次我们不修改栈顶元素 ,只是将栈顶元素赋值给 e
//传入栈指针和存储取顶元素的指针
bool GetTop(SqStack *s , ElemType &e)
{
	//如果栈空,则返回false,无元素不可取元素
	if(s->top == -1)
	{
		return false;
	}
	//如果栈不空,则把栈顶元素传入取元素的指针e
	e = s -> data[s->top];
	return true;	
}

  • 4
    点赞
  • 20
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值