栈和队列
栈——后进先出
表的一段进行插入和删除的操作
栈的顺序存储
静态顺序栈
用一维数组存储,栈底不变,栈顶指针top(整型变量)指向当前栈顶的位置
定义
#define MAX_STACK_SIZE 100
#typedef int ElemType;
typedef struct sqstack
{
ElemType stack_arry[MAX_STACK_SIZE];
int top;
}SqStack;
初始化
SqStack Init_Stack(void)
{
SqStack S;
S.bottom=S.top=0;
return(s);
}
出栈
Status pop(SqStack &S,ElemType &e)
{
if(S.top==0)
return ERROR;//栈空,返回错误
*e=S.stack_array[S.top];
S.top--;
return OK;
}
入栈
Status push(SqStack&S,ElemType &e)
{
if(S.top==MAX_STACK_SIZE-1)
return ERROR;//栈满,因为是从0开始计数的
S.top++;
S.stack_array[S.top]=e;
return OK;
}
动态顺序栈
top指向栈顶的下一个存储位置
定义
#define STACK_SIZE 100//栈的初始向量的大小
#define STACKINCREMENT 10//存储空间分配的增量
#typedef int ElemType;
typedef struct sqstack
{
ElemType *bottom;//栈不存在时为NULL
ElemType *top;//栈顶指针
int stacksize;
}SqStack;
初始化
Status Init_Stack(void)
{
SqStack S;
S.bottom=(ElemType*)malloc(STACK_SIZE*sizeof(ElemType));
if(!S.bottom)
return ERROR;
S.top=S.bottom;//令栈顶和栈底指针相同
S.stacksize=STACK_SIZE;
return OK;
}
出栈(弹栈)
pop(SqStack &S,ElemType &)
{
if(S.top==S.bottom)
return ERROR;
S.top--;//因为top始终指向栈顶的下一个
e=*S.top;
return OK;
}
入栈
Status push(SqStack &S,ElemType e)
{
if(S.top-S.bottom>=S.stacksize-1)
{
S.bottom=(ElemType*)realloc((S.STACKINCREMENT+STACK_SIZE)*sizeof(ElemType));
if(!S.bottom)
return ERROR;
S.top=S.bottom+S.stacksize;
S.stacksize+=STACKINCREMENT;
}
*S.top=e;
S.top++;
return OK;
}
栈的链式存储
栈顶指针top是链表的头指针
栈的结点类型说明
typedef struct Stack_Node
{
ElemType data;
structStack_Node *next;
}Stack_Node;
栈的初始化
Stack_Node*Init_Link_Stack(void)
{
Stack_Node*top;
top=(Stack_Node*)malloc(sizeof(Stack_Node);
top->next=NULL;
return(top)
}
出栈(弹栈)
Status pop(Stack_Node *top,ElemType *e)
{
Stack_Node *p;
ElemType e;
if(top->next==NULL)
return ERROR;
p=top->next;
e=p->data;
top->next=p->next;
free(p);
return OK;
}
压栈
Status push(Stack_Node*top,ElemType)
{
Stack_Node *p;
p=(Stack_Node*)malloc(sizeof(Stack_Node));
if(!p)
return ERROR;
p->data=e;
p->next=top->next;
top->next=p;
return OK;
}
队列——先进先出
基本概念
队列Queue
队首front:允许进行删除的一端
队尾rear:允许进行插入的一段
队列的顺序结构
表示
#define MAX_QUEUE_SIZE 100;
typedef struct queue
{
ElemType Queue_array[MAX_QUEUE_SIZE];
int front;
int rear;
}SqQueue;
初始化:front=rear=0
入队:将新元素插入rear所指的的位置,然后rear加1
出队:删去front所指的元素,然后加1并返回被删元素
队列为空:front=rear
队满:rear=MAX_QUEUE_SIZE-1
存在假溢出现象
循环队列
循环队列为空:front=rear
循环队列满:(rear+1)%MAX_QUEUE_SIZE=front
初始化
SqQueue Init_CirQueue(void)
{
SqQueue Q;
Q.front=Q.rear=0;
return (Q);
}
入队
Status Insert_CirQueue(SqQueue &Q,ElemType e)
{
if((Q.rear+1)%MAX_QUEUE_SIZE==Q.front)
return ERROR;
Q.Queue_array[Q.rear]=e;
Q.rear=(Q.rear+1)%MAX_QUEUE_SIZE;//队尾指针加1
return OK;
}
出队
Status Delete_CriQueue(SqQueue &Q,ElemType *x)
{
if(Q.front==Q.rear)
return ERROR;
*x=Q.Queue_array[Q.front];
Q.front=(Q.front+1)%MAX_QUEUE_SIZE;//队首指针向前移动
return OK;
}
队列的链式存储结构
数据元素结点的类型定义
typedef struct Qnode
{
ElemType data;
struct Qnode *next;
}QNode;
链队列初始化
LinkQueue *Init_LinkQueue(void)
{
LinkQueue *Q;
QNode *p;
p=(QNode*)malloc(sizeof(QNode));//开辟头结点
p->next=NULL;
Q=(LinkQueue*)malloc(sizeof(LinkQueue));//开辟链队的指针结点
Q.front=Q.rear=p;
return (Q);
}
入队
将数据元素e插入到链队列的Q的队尾
Status Insert_CriQueue(LinkQueue *Q,ElemType e)
{
p=(QNode*)malloc(sizeof(QNode));
if(!p)//申请空间失败
return ERROR;
p->data=e;
p->next=NULL;//先勾右边
Q.rear->next=p;//再勾左边
Q.rear=p;
return OK;
}
出队
Status Delete_LinkQueue(LinkQueue *Q,ElemType *x)
{
QNode*p;
if(Q.front==Q.rear)//队空
return ERROR;
p=Q.front->next;//取队首结点
*x=p->data;
Q.front->next=p->next;//修改首指针
if(p==Q.rear)
Q.rear=Q.front;
free(p);
return OK
}
队列的撤销
将链队Q 的队首元素依次出队
void Destory_LinkQueue(LinkQueue *Q)
{
QNode*p=NULL;
if(Q.front)p=Q.front->next;
while(p->next)
{
QNode *q=p->next;
free(p);
p=q;
}
Q.front->next=NULL;
Q.rear=Q.front;
}