一.队列定义及性质
1.性质
(1)队列是一种运算受限的线性表,只能在队头进行删除操作,在队尾进行插入操作。
“先进先出”(可以用现实生活中的排队去思考)
(所以我们可以用对头和队尾来对队列进行操作)
(2)空队列:队中没有元素时
2.结构类型
(1)使用顺序存储结构
#include <stdio.h>
#include<stdlib.h>
#define MAXSIZE 1000
typedef int Datatype;
//队的顺序存储结构
typedef struct{
Datatype data[MAXSIZE];
int front,rear;
}SequenQueue;
//front为对头指针,rear为队尾指针
(2)使用链式存储结构
#include <stdio.h>
#include<stdlib.h>
#define MAXSIZE 1000
typedef int Datatype;
//链表
typedef struct node{
Datatype data;
struct node *next;
}LinkList;
//链队列
typedef struct{
LinkList *front,*rear;
}LinkQueue;
二.队列的运算
1.循环队列
由上图操作可以看出当入队时候会出现“假上溢”的情况,这时有大部分的空间都会被浪费掉。
为了解决空间浪费问题,有三种方法:
(1)每次入队的时候都将队列整体向前移动一个位置,很像我们日常生活中的排队,前面有位置就向前移动。但是日常排队人数不会太多,在处理大量的数据时这种整体移动是很复杂麻烦的,效率也很低。
(2)每当出现“假上溢”的情况,就把队列整体移动到初始位置。此时我们除了判断假上溢的情况外,还要进行移动,效率也很低。
(3)运用循环队列解决。
由上面两图可以看出,入队在队尾进行操作,队尾位置++,出队在队头进行操作,队头位置++;
循环队列的运算:
#include <stdio.h>
#include<stdlib.h>
#define MAXSIZE 1000
typedef int Datatype;
typedef struct{
Datatype data[MAXSIZE];
int front,rear;
}SequenQueue;
//置空栈(初始化)SetNULLQ
SequenQueue *SetNULLQ(SequenQueue *sq){
sq = (SequenQueue *)malloc(sizeof(SequenQueue));
sq->front=MAXSIZE-1;
sq->rear=MAXSIZE-1;
return sq;
}
//判断是否为空 EmptyQ
Datatype EmptyQ(SequenQueue *sq){
if(sq->front=sq->rear){
return 1;
}
else{
return 0;
}
}
//取队头元素 FrontQ
Datatype *FrontQ(SequenQueue *sq){
Datatype *ret;
if(EmptyQ(sq)){
printf("为空队,没有队头元素");
return NULL;
}
else{
ret = (Datatype *)malloc(sizeof(Datatype));
*ret = sq->data[(sq->front+1)%MAXSIZE];
return ret;
}
}
//元素入队 EnQueueQ
int EnQueueQ(SequenQueue *sq,Datatype x){
if((sq->rear+1)%MAXSIZE==sq->front){
printf("队满,无法入队");
return 0;
}else{
sq->rear=(sq->rear+1)%MAXSIZE;
sq->data[sq->rear]=x;
return 1;
}
}
//出队并返回队头元素 DeQuenueQ
Datatype *DeQuenueQ(SequenQueue *sq){
Datatype *ret;
if(EmptyQ(sq)){
printf("为空队,没有队头元素");
return NULL;
}else{
ret = (Datatype *)malloc(sizeof(Datatype));
*ret = sq->data[(sq->front+1)%MAXSIZE];
sq->front=(sq->front+1)%MAXSIZE;
return ret;
}
}
2.链队列
#include <stdio.h>
#include<stdlib.h>
#define MAXSIZE 1000
typedef int Datatype;
//链表
typedef struct node{
Datatype data;
struct node *next;
}LinkList;
//链队列
typedef struct{
LinkList *front,*rear;
}LinkQueue;
//置空队并初始化 SetNULLQ
LinkQueue *SettNULLQ(LinkQueue *q){
q = (LinkQueue *)malloc(sizeof(LinkQueue));
q->front->next=NULL;
q->rear=q->front;
return q;
}
//判断空队 EmptyQ
int EmptyQ(LinkQueue *q){
if(q->front==q->rear)
return 1;
else
return 0;
}
//取队头元素 FrontQ
Datatype *FrontQ(LinkQueue *q){
Datatype *ret;
if(EmptyQ(q)){
printf("队为空,没有队头元素");
return NULL;
}else{
ret = (Datatype *)malloc(sizeof(Datatype));
*ret = q->front->next->data;
return ret;
}
}
//入队 EnQuenueQ
void EnQuenueQ(LinkQueue *q,Datatype x){
q->rear->next = (LinkList *)malloc(sizeof(LinkList));
q->rear=q->rear->next;
q->rear->data=x;
q->rear->next=NULL;
}
//出队 DeQuenueQ
Datatype *DeQuenueQ(LinkQueue *q){
Datatype *ret;
LinkList *s;
if(EmptyQ(q)){
printf("队为空,没有队头元素");
return NULL;
}else{
s = q->front->next;
if(s->next=NULL){
q->front->next=NULL;
q->rear=q->front;
}else{
q->front->next=q->front->next->next;
}
ret = (Datatype *)malloc(sizeof(Datatype));
*ret = s->data;
free(s);
return ret;
}
}