2.1、堆栈(Stack):具有一定操作约束的线性表
只在一端(栈顶,Top)做 插入、删除
插入数据:入栈(Push)
删除数据:出栈(Pop)
后入先出:Last In First Out(LIFO)
2.2、 基本操作
//操作集:长度为MaxSize的堆栈S Stack,堆栈元素item<-ElementType
Stack CreateStack( int MaxSize ): 生成空堆栈,其最大长度为MaxSize;
int IsFull( Stack S, int MaxSize ):判断堆栈S是否已满;
void Push( Stack S, ElementType item ):将元素item压入堆栈;
int IsEmpty ( Stack S ):判断堆栈S是否为空;
ElementType Pop( Stack S ):删除并返回栈顶元素;
2.3、栈的顺序存储实现(通常由一个一维数组和一个记录栈顶元素位置的变量组成。)
#define MaxSize <储存数据元素的最大个数>
typedef struct SNode *Stack;
struct SNode{
ElementType Data[MaxSize];
int Top;
};
(1)入栈
void Push( Stack PtrS, ElementType item )
{
if ( PtrS->Top == MaxSize-1 ) {
printf(“堆栈满”); return;
}else {
PtrS->Data[++(PtrS->Top)] = item;//将item放栈顶,并且将栈顶容量++;
return;
}
}
(2)出栈
ElementType Pop( Stack PtrS )
{
if ( PtrS->Top == -1 ) {
printf(“堆栈空”);
return ERROR; /* ERROR是ElementType的特殊值,标志错误 */
} else
return ( PtrS->Data[(PtrS->Top)--] );
}
[例] 请用一个数组实现两个堆栈,要求最大地利用数组空间,使数组只要有空间入栈操作就可以成功。
/*【分析】 一种比较聪明的方法是使这两个栈分别从数组的两头开始向中间生长;当两
个栈的栈顶指针相遇时,表示两个栈都满了。*/
#define MaxSize<存储数据元素的最大个数>
struct D Stack{
ElementType Data[MaxSize];
int Top1;
int Top2;
}S;
S.Top = -1;
S.Top = MaxSize;
void Push(struct DStack *PtrS,ElementType item,int Tag){
/* Tag作为区分两个堆栈的标志,取值为1和2 */
if(PtrS->Top2-PtrS->Top1==1){
printf("堆栈满");
}
if(Tag==1){ /* 对第一个堆栈操作 */
PtrS->Data[++(PtrS->Top1)]=item;
}else{
PtrS->Data[--(PtrS->Top2)]==item;
}
}
ElementType Pop(struct DStack *PtrS,int Tag){
if(Tag==1){
if(PtrS->Top1==-1)
printf("堆栈1空");return NULL;
else return PtrS->Data[(PtrS->Top)--];
}else{
if(PtrS->Top2==MaxSize){
printf("堆栈2空");return NULL;
}else return PtrS->Data[(PtrS->Top2)++];
}
}
2.4、堆栈的链式存储(实际上就是一个单链表,叫做链栈。)
插入和删除操作只能在链栈的栈顶进行。
若用单向链表实现一个堆栈,只能用链表的头作为top,因为若是用尾作为top的话,虽然插入没毛病,但是由于是单向链表删除top元素后就找不到栈顶了
typedef struct SNode *Stack;
struct SNode{
ElementType Data;
struct SNode *Next;
};
//堆栈初始化
Stack CreateStack(){
Stack S;
S = (Stack)malloc(sizeof(struct SNode));
S->Next = NULL;
return S;
}
//判空
int IsEmpty(Stack S){
return (S->Next == NULL);
}
//将元素item压入堆栈S
void Push(ElementType Stack S){
struct SNode *TmpCell;
TmpCell = (struct SNode *)malloc(sizeof(struct SNode));
TmpCell->Element = item;
TmpCell->Next=S->Next;
S->Next = TmpCell;
}
//删除并返回堆栈S的栈顶元素
ElementType Pop(Stack S){
struct SNode *FirstCell;
ElementType TopElem;
if(IsEmpty(S)){
printf("堆栈空"); return NULL;
}else{
FirstCell = S->Next;
S->Next = FirstCell->Next;
TopElem = FirstCell->Element;
free(FirstCell);
return TopElem;
}
}