第4章栈和队列:顺序栈的基本概念和操作

4.2 顺序栈

栈是一种操作受限的线性表,在第 3 章中已经讲过,逻辑结构数据的存储结构有两种:顺序存储和链式存储。所以,栈也可以用顺序结构和链式结构两种方式表示,本节将介绍顺序结构的表示方法。

4.2.1 顺序栈的存储结构

顺序栈(Sequential Stack)是指利用顺序存储结构实现的栈,即利用一组地址连续的存储单元依次存放自栈底到栈顶的数据元素,同时附设指针 top 指示栈顶元素在顺序栈中的位置。

若以顺序表为例,top 指针所指示的使表尾,在表尾进行元素的插入或删除,时间复杂度都是 O(1)O(1)O(1) ,不需要移动元素。所以,顺序栈和顺序表的存储结构本质是相同的,差别进在于增加了指针,并且规定只能在“表尾”(即栈顶)进行操作。

顺序栈的存储结构:

#define MAXSIZE 100 //顺序栈存储空间的初始分配量
typedef struct{
    SElemType *base; //栈底指针
    SElemType *top; //栈顶指针
    int stacksize;  //栈可用的最大容量
}SqStack;
  • base 为栈底指针,初始化完成后,栈底指针 base 始终指向栈底位置,若 base 的值为 NULL ,则表明栈结构不存在。

  • top 为栈顶指针,初始值指向栈底。每当插入新的栈顶元素时,指针 top 增 1;删除栈顶元素时,指针 top 减 1。

  • 栈空时,topbase 的值相等,都指向栈底;栈非空时,top 始终指向栈顶元素的上一个位置。图 4.2.1 显示了栈中的元素和栈指针之间的关系。

  • stacksize 指示栈可使用的最大容量。

在这里插入图片描述

图 4.2.1 顺序栈的操作

参考图 4.2.1 ,可知顺序栈 S 的“空”“满”的条件:

  • 栈空的条件:S.base == S.top
  • 栈满的条件:S.top - S.base == S.stacksize

4.2.2 顺序栈的基本操作

1. 顺序栈的初始化

顺序栈的初始化就是为顺序栈动态分配一个预定义大小的数组空间。

【算法步骤】

  1. 为顺序栈动态分配一个最大容量为 MAXSIZE 的数组空间,使 base 指向这段空间的基地址,即栈底。
  2. 栈顶指针 top 初始为 base ,表示栈为空。
  3. stacksize 置为栈的最大容量 MAXSIZE

【算法描述】

Status InitStack(SqStack &S){//构造一个空栈 S
    //为顺序栈动态分配一个最大容量为 MAXSIZE 的数组空间
    S.base = new SElemType[MAXSIZE]; 
    if(!S.base)
        exit(OVERFLOW); //存储分配失败
    S.top = S.base;  //top 初始为 base, 空栈
    S.stacksize = MAXSIZE; //stacksize 置为栈的最大容量 MAXSIZE
    return OK;
}

【算法分析】

时间复杂度 O(1)O(1)O(1)

2. 顺序栈的入栈

入栈操作:在栈顶插入一个新的元素,如图 4.2.1 所示。

【算法步骤】

  1. 判断栈是否满,若满则返回 ERROR
  2. 将新元素压入栈顶,栈顶指针加 1。

【算法描述】

Status Push(SqStack &S, SElemType e){
    //插入元素 e 为新的栈顶元素
    if(S.top - S.base == S.stacksize)
        return ERROR; //栈满
    
    // 入栈操作:先赋值,再移动栈顶指针
    *(S.top) = e;  
    S.top++;       
    
    return OK;
}

【算法分析】

时间复杂度:O(1)O(1)O(1)

3. 顺序栈的出栈

出栈操作:将栈顶元素删除。

【算法步骤】

  1. 判断栈是否为空,若空则返回 ERROR。
  2. 栈顶指针减 1,栈顶元素出栈。

【算法描述】

Status Pop(SqStack &S, SElemType &e){
    //删除 S 的栈顶元素,用 e 返回其值
    if(S.top == S.base)
        return ERROR;   //栈空
    
    // 正确的出栈操作:先移动指针,再获取元素值
    e = *(--S.top); // 等价于: S.top--; e = *S.top;
    
    return OK;
}

【算法分析】

时间复杂度:O(1)O(1)O(1)

4. 取顺序栈的栈顶元素

取栈顶元素的操作:当栈非空时,返回当前栈顶元素的值,栈顶指针保持不变。

【算法描述】

SElemType GetTop(SqStack S){
    //返回 S 的栈顶元素,不修改栈顶指针
    if(S.top != S.base)//栈非空
        return *(S.top - 1); //返回栈顶元素值,栈顶指针不变
}

【算法分析】

时间复杂度:O(1)O(1)O(1)

例 4.2.1 若一个栈以向量 V[1..n] 存储,初始栈顶指针 top 设为 n+1,则元素 x 进栈的正确操作是( )。

A. top++; V[top]=x; \qquad B. V[top]=x; top++;

C. top--; V[top]=x; \qquad D. V[top]=x; top--;

【解】

初始栈顶指针 topn+1,说明元素从数组向量的高端地址进栈,又因为元素存储在向量空间 V[1..n] 中,所以进栈时 top 指针先下移变为 n,之后将元素 x 存储在 V[n]

本题答案:C

例 4.2.2 在一个有 nnn 个单元的顺序栈中,假定以地址高端(下标为 n−1n-1n1 的单元)作为栈底,以 top 作为栈顶指针,则向栈中压入一个元素时,top 的变化是 ( )。

A. top 不变\qquad B. top = n\qquad C. top = top - 1\qquad D. top = top + 1

【解】

栈底为 n−1n-1n1 处,若有元素进栈,该元素应首先占有高地址的单元,因此栈顶指针 top 应减 1。

本题答案:C

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

CS创新实验室

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值