队列的实现
一、顺序队列
- typedef int QElemType;
- // c3-3.h 队列的顺序存储结构(可用于循环队列和非循环队列)
- #define MAXQSIZE 5 // 最大队列长度(对于循环队列,最大队列长度要减1)
- struct SqQueue
- {
- QElemType *base; // 初始化的动态分配存储空间
- int front; // 头指针,若队列不空,指向队列头元素
- int rear; // 尾指针,若队列不空,指向队列尾元素的下一个位置
- };
- // bo3-4.cpp 顺序队列(非循环,存储结构由c3-3.h定义)的基本操作(9个)
- Status InitQueue(SqQueue &Q)
- { // 构造一个空队列Q
- Q.base=(QElemType *)malloc(MAXQSIZE*sizeof(QElemType));
- if(!Q.base) // 存储分配失败
- exit(OVERFLOW);
- Q.front=Q.rear=0;
- return OK;
- }
- Status DestroyQueue(SqQueue &Q)
- { // 销毁队列Q,Q不再存在
- if(Q.base)
- free(Q.base);
- Q.base=NULL;
- Q.front=Q.rear=0;
- return OK;
- }
- Status ClearQueue(SqQueue &Q)
- { // 将Q清为空队列
- Q.front=Q.rear=0;
- return OK;
- }
- Status QueueEmpty(SqQueue Q)
- { // 若队列Q为空队列,则返回TRUE,否则返回FALSE
- if(Q.front==Q.rear) // 队列空的标志
- return TRUE;
- else
- return FALSE;
- }
- int QueueLength(SqQueue Q)
- { // 返回Q的元素个数,即队列的长度
- return(Q.rear-Q.front);
- }
- Status GetHead(SqQueue Q,QElemType &e)
- { // 若队列不空,则用e返回Q的队头元素,并返回OK,否则返回ERROR
- if(Q.front==Q.rear) // 队列空
- return ERROR;
- e=*(Q.base+Q.front);
- return OK;
- }
- Status EnQueue(SqQueue &Q,QElemType e)
- { // 插入元素e为Q的新的队尾元素
- if(Q.rear>=MAXQSIZE)
- { // 队列满,增加1个存储单元
- Q.base=(QElemType *)realloc(Q.base,(Q.rear+1)*sizeof(QElemType));
- if(!Q.base) // 增加单元失败
- return ERROR;
- }
- *(Q.base+Q.rear)=e;
- Q.rear++;
- return OK;
- }
- Status DeQueue(SqQueue &Q,QElemType &e)
- { // 若队列不空,则删除Q的队头元素,用e返回其值,并返回OK,否则返回ERROR
- if(Q.front==Q.rear) // 队列空
- return ERROR;
- e=Q.base[Q.front];
- Q.front=Q.front+1;
- return OK;
- }
- Status QueueTraverse(SqQueue Q,void(*vi)(QElemType))
- { // 从队头到队尾依次对队列Q中每个元素调用函数vi()。一旦vi失败,则操作失败
- int i;
- i=Q.front;
- while(i!=Q.rear)
- {
- vi(*(Q.base+i));
- i++;
- }
- printf("\n");
- return OK;
- }
二、链队列
- typedef int QElemType;
- // c3-2.h 单链队列--队列的链式存储结构
- typedef struct QNode
- {
- QElemType data;
- QNode *next;
- }*QueuePtr;
- struct LinkQueue
- {
- QueuePtr front,rear; // 队头、队尾指针
- };
- // bo3-2.cpp 链队列(存储结构由c3-2.h定义)的基本操作(9个)
- Status InitQueue(LinkQueue &Q)
- { // 构造一个空队列Q
- if(!(Q.front=Q.rear=(QueuePtr)malloc(sizeof(QNode))))
- exit(OVERFLOW);
- Q.front->next=NULL;
- return OK;
- }
- Status DestroyQueue(LinkQueue &Q)
- { // 销毁队列Q(无论空否均可)
- while(Q.front)
- {
- Q.rear=Q.front->next;
- free(Q.front);
- Q.front=Q.rear;
- }
- return OK;
- }
- Status ClearQueue(LinkQueue &Q)
- { // 将Q清为空队列
- QueuePtr p,q;
- Q.rear=Q.front;
- p=Q.front->next;
- Q.front->next=NULL;
- while(p)
- {
- q=p;
- p=p->next;
- free(q);
- }
- return OK;
- }
- Status QueueEmpty(LinkQueue Q)
- { // 若Q为空队列,则返回TRUE,否则返回FALSE
- if(Q.front==Q.rear)
- return TRUE;
- else
- return FALSE;
- }
- int QueueLength(LinkQueue Q)
- { // 求队列的长度
- int i=0;
- QueuePtr p;
- p=Q.front;
- while(Q.rear!=p)
- {
- i++;
- p=p->next;
- }
- return i;
- }
- Status GetHead(LinkQueue Q,QElemType &e)
- { // 若队列不空,则用e返回Q的队头元素,并返回OK,否则返回ERROR
- QueuePtr p;
- if(Q.front==Q.rear)
- return ERROR;
- p=Q.front->next;
- e=p->data;
- return OK;
- }
- Status EnQueue(LinkQueue &Q,QElemType e)
- { // 插入元素e为Q的新的队尾元素
- QueuePtr p;
- if(!(p=(QueuePtr)malloc(sizeof(QNode)))) // 存储分配失败
- exit(OVERFLOW);
- p->data=e;
- p->next=NULL;
- Q.rear->next=p;
- Q.rear=p;
- return OK;
- }
- Status DeQueue(LinkQueue &Q,QElemType &e)
- { // 若队列不空,删除Q的队头元素,用e返回其值,并返回OK,否则返回ERROR
- QueuePtr p;
- if(Q.front==Q.rear)
- return ERROR;
- p=Q.front->next;
- e=p->data;
- Q.front->next=p->next;
- if(Q.rear==p)
- Q.rear=Q.front;
- free(p);
- return OK;
- }
- Status QueueTraverse(LinkQueue Q,void(*vi)(QElemType))
- { // 从队头到队尾依次对队列Q中每个元素调用函数vi()。一旦vi失败,则操作失败
- QueuePtr p;
- p=Q.front->next;
- while(p)
- {
- vi(p->data);
- p=p->next;
- }
- printf("\n");
- return OK;
- }
三、循环队列
- // c3-3.h 队列的顺序存储结构(可用于循环队列和非循环队列)
- #define MAXQSIZE 5 // 最大队列长度(对于循环队列,最大队列长度要减1)
- struct SqQueue
- {
- QElemType *base; // 初始化的动态分配存储空间
- int front; // 头指针,若队列不空,指向队列头元素
- int rear; // 尾指针,若队列不空,指向队列尾元素的下一个位置
- };
- // bo3-3.cpp 循环队列(存储结构由c3-3.h定义)的基本操作(9个)
- Status InitQueue(SqQueue &Q)
- { // 构造一个空队列Q
- Q.base=(QElemType *)malloc(MAXQSIZE*sizeof(QElemType));
- if(!Q.base) // 存储分配失败
- exit(OVERFLOW);
- Q.front=Q.rear=0;
- return OK;
- }
- Status DestroyQueue(SqQueue &Q)
- { // 销毁队列Q,Q不再存在
- if(Q.base)
- free(Q.base);
- Q.base=NULL;
- Q.front=Q.rear=0;
- return OK;
- }
- Status ClearQueue(SqQueue &Q)
- { // 将Q清为空队列
- Q.front=Q.rear=0;
- return OK;
- }
- Status QueueEmpty(SqQueue Q)
- { // 若队列Q为空队列,则返回TRUE,否则返回FALSE
- if(Q.front==Q.rear) // 队列空的标志
- return TRUE;
- else
- return FALSE;
- }
- int QueueLength(SqQueue Q)
- { // 返回Q的元素个数,即队列的长度
- return(Q.rear-Q.front+MAXQSIZE)%MAXQSIZE;
- }
- Status GetHead(SqQueue Q,QElemType &e)
- { // 若队列不空,则用e返回Q的队头元素,并返回OK,否则返回ERROR
- if(Q.front==Q.rear) // 队列空
- return ERROR;
- e=*(Q.base+Q.front);
- return OK;
- }
- Status EnQueue(SqQueue &Q,QElemType e)
- { // 插入元素e为Q的新的队尾元素
- if((Q.rear+1)%MAXQSIZE==Q.front) // 队列满
- return ERROR;
- Q.base[Q.rear]=e;
- Q.rear=(Q.rear+1)%MAXQSIZE;
- return OK;
- }
- Status DeQueue(SqQueue &Q,QElemType &e)
- { // 若队列不空,则删除Q的队头元素,用e返回其值,并返回OK;否则返回ERROR
- if(Q.front==Q.rear) // 队列空
- return ERROR;
- e=Q.base[Q.front];
- Q.front=(Q.front+1)%MAXQSIZE;
- return OK;
- }
- Status QueueTraverse(SqQueue Q,void(*vi)(QElemType))
- { // 从队头到队尾依次对队列Q中每个元素调用函数vi().一旦vi失败,则操作失败
- int i;
- i=Q.front;
- while(i!=Q.rear)
- {
- vi(*(Q.base+i));
- i=(i+1)%MAXQSIZE;
- }
- printf("\n");
- return OK;
- }
微信公众号:
猿人谷
如果您认为阅读这篇博客让您有些收获,不妨点击一下右下角的【推荐】
如果您希望与我交流互动,欢迎关注微信公众号
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接。