导言
栈是线性表的一种特殊形式,故而有两种存储方式,现今讨论顺序栈
栈的存储表示方式
顺序栈(顺序存储结构)
利用一组地址连续的存储单元依次存放自栈底到栈顶的数据元素,同时附设指针top指示栈顶元素在顺序栈中的位置。
top=0,表示空栈
设计过程中初始化空栈,是先为栈分配一个基本容量,然后在应用过程中逐渐扩大。因此可以为此设定两个常量
STACK_INIT_SIZE(存储空间初始分配量)
STACKINCREMENT(存储空间分配增量)
顺序栈的定义
typedef struct
{
SElemType *base;
SElemType *top;
int stacksize;
}SqStack;
stacksize指示栈的当前可使用的最大容量
栈的初始化操作
按设定的初始分配量进行第一次存储分配,base为栈底指针,顺序栈中,它始终指向栈底的位置,若base的值为NULL,则表明栈结构不存在。称top为栈顶指针,其初值指向栈底,即top=base表示栈空。当插入新的栈顶元素时,top增1;删除栈顶元素时,指针top减1,因此,非空栈中的栈顶指针始终在栈顶元素的下一个位置上(以倒过来看,栈顶指针指向栈顶元素的上方位置,而以存储结构来看,栈顶指针指向元素存储位置的下一个元素的位置)。
栈顶指针和栈中元素的关系
顺序栈的模块说明
// ====== ADT Stack 的表示和实现 =====
// ----- 栈的顺序存储表示 -----
#define STACK_INIT_SIZE 100; //存储空间初始分配量
#define STACKINCREMENT 10; //存储空间分配增量
typedef struct
{
SElemType *base;//在构造之前和销毁之后,base的值为NULL
SElemType *top;//栈顶指针
int stacksize;//当前已分配的存储空间,以元素为单位
}SqStack;
// ----- 基本操作的函数原型说明 -----
InitStack(SqStack &S)
//构造一个空栈 S。
DestroyStack(SqStack &S)
//销毁栈S,S不再存在
ClearStack(&SqStack)
//把S置为空栈
StackEmpty(SqStack S)
//若S为空栈,则返回TRUE,否则返回FALSE
StackLength(SqStack S)
//返回S的元素个数,即栈的长度
GetTop(SqStack S,SElemType &e)
//若栈不空,则用e返回S的栈顶元素,并返回OK;否则返回ERROR
Push(SqStack &S,SElemType &e)
//插入元素e为新的栈顶元素
Pop(SqStack &S,SElemType &e)
//若栈不空,则删除S的栈顶元素,用e返回其值,并返回OK;否则返回ERROR
StackTraverse(SqStack S,Status (*visit)())
//从栈底到栈顶依次对S的每个元素调用函数visit()。一旦visit( )失败,则操作失败。
// ----- 基本操作的算法描述(部分) -----
Status InitStack(SqStack &S)
{
//构造一个空栈
S.base = (SElemType)malloc(STACK_INIT_SIZE * sizeof(SElemType));
if(!S.base)exit(OVERFLOW);//存储分配失败
S.top = S.base;
S.stacksize = STACK_INIT_SIZE;
return OK;
}//InitStack
Status GetTop(SqStack S,SElemType &e)
{
if(S.top == S.base)return ERROR;
e = *(S.top - 1);
return OK;
}//GetTop
Status Push(SqStack &S,SElemType &e)
{
//插入元素e为新的栈顶元素
if(S.top - S.base >= S.stacksize)
{//栈满,追加存储空间
S.base = (SElemType *)realloc(S.base,(S.stacksize,STACKINCREMENT)*sizeof(SElemType));
if(!S.base)exit(OVERFLOW);
S.top = S.base + S.stacksize;
S.stacksize += STACKINCREMENT;
}
*S.top++ = e;
return OK;
}//push
Status Pop(SqStack &S,SElemType &e)
{//若栈不空,则删除S的栈顶元素,用e返回其值,并返回OK;否则返回ERROR
if(S.top == S.base)return ERROR;
e = *--S.top;
return OK;
}//pop
结语
顺序栈的用途还是广泛的,后面的阶段会展开具体实现。
栈的链式存储方式,会看情况进行解析。