前面我们讲了线性表,今天讲的栈其实也是一种特殊的线性表。表头叫栈底(bottom),表尾叫栈顶(top)。栈为空栈时,栈顶就是栈底。
栈(stack)的特殊性体现在它的操作上:
1、后进先出(LIFO:last in first out)
2、只允许在表尾(栈顶)进行操作:栈的插入操作(push)叫进栈,压栈,入栈;栈的删除操作(pop)叫出栈,弹栈。
接下来,我们来了解以下栈的顺序存储结构的相关操作。
1、栈的声明
typedef struct
{
ElemType *base;//指向栈底的指针变量
ElemType *top;//指向栈顶的指针变量
int stacksize;//栈当前可使用的最大容量
}sqStack;
2、入栈
首先我们要知道,base指针一直指向栈底,top指针指向栈顶,注意,如果说栈里如果现在有三个元素a,b,c;那么base指向a,top不是指向c,top指向c上面一个空位置!!压入一个元素,top就要往上移一个位置,直到压满追加空间。
栈满的判断条件是:s->top-s->base>=s->stacksize(由于top指向表尾,base指向表头,自然top比base大)
如果栈满,追加空间有三步:
s->base=(ElemType *)realloc(s->base,(s->stacksize+addsize)*sizeof(ElemType));
s->top=s->base+s->stacksize;
s->stacksize=s->stacksize+addsize;
如果栈未满,把元素压入栈,top指针上移即可:
*(s->top)=e;
s->top++;
3、出栈
我们要知道栈的操作只在栈顶进行,要操作前我们要先把top指针移到我们要操作位置处,如果是入栈就不用移了,入完top上移即可。可是出栈前需要移动top到下一位置,也就是要出栈的那个元素处,取出元素返回即可。直到空栈就停止。
空栈的判断条件:s->top==s->base
下移指针并取出元素:*e=*--(s->top)
4、清空栈
清空栈是清空其中的元素,而非栈的物理空间,也就是不用释放空间!!
直接s->top=s->base即可
5、销毁栈
销毁栈需要释放栈所占的物理空间,与清空栈不同!!
循环遍历再free,最后不要忘了设置栈的三个量:s->base=s->top=NULL;s->stacksize=0;
6、返回栈的当前容量
我们这里需要区分当前容量和最大容量:最大容量就是s.stackbase,当前容量就是s.top-s.base
注:若定义sqstack *s,这里s是指针,需要用“->"调用变量;若定义sqstack s,这里用”.“调用变量!!
BY ZJQ