队列的顺序实现
1、定义和初始化
//队列的定义
typedef struct{
int data[maxsize];
int front,rear;
}SqQueue;
//队列初始化
void InitQueue(SqQueue &Q){
//队头队尾指针都指向data[0]
Q.rear=Q.front=0;
}
2、判空
//队列判空
bool Empty(SqQueue){
if(Q.rear==Q.front)
return true;
else
returnn false;
}
3、循环队列入队
方式一
//方法1 牺牲一个存储单元区别队空和队满
bool EnQueue(SqQueue &Q,int x){
if((Q.rear+1)%maxsize=Q.front)//队列已满
return false;
//队尾指针指向队列最后一个元素的下一个位置
Q.data=x;
Q.rear=(Q.rear+1)%maxsize;//如果队头有元素出队,队尾已满,元素将插入队头空闲位置
return true;
}
方式二
//方法2,多初始化一个变量,记录队列中存放的数据元素
typedef struct{
int data[maxsize];
int front,rear,size;
}SqQueue;
void InitQueue(SqQueue &Q){
//队头队尾指针都指向data[0]
Q.rear=Q.front=0;
Q.size=0;//相应地,队空条件为size==0;
}
bool EnQueue(SqQueue &Q,int x){
if(size==maxsize)//队列已满
return false;
//队尾指针指向队列最后一个元素的下一个位置
Q.data=x;
Q.rear=(Q.rear+1)%maxsize;//如果队头有元素出队,队尾已满,元素将插入队头空闲位置
Q.size++;//同理,删除一个元素size--
return true;
}
方式3
//方法3,初始化一个标记变量tag,记录前一步操作是插入还是删除
typedef struct{
int data[maxsize];
int front,rear,tag;//每次删除成功tag=0,插入成功tag=1;
}SqQueue;
void InitQueue(SqQueue &Q){
//队头队尾指针都指向data[0]
Q.rear=Q.front=0;
}
bool EnQueue(SqQueue &Q,int x){
if(Q.rear==Q.front&&Q.tag=1)//队列已满
return false;
//队尾指针指向队列最后一个元素的下一个位置
Q.data=x;
Q.rear=(Q.rear+1)%maxsize;//如果队头有元素出队,队尾已满,元素将插入队头空闲位置
//插入成功
Q.tag=1;
return true;
}
4、循环队列出队
//循环队列出队——删除一个队头元素,并用x返回
bool DeQueue(SqQueue &Q,int &x){
//队列为空
if(Q.rear==Q.front&&Q.tag=0)
return false;
x=Q.dada[Q.front];
//循环队列指针后移,相当于删除了队头元素,如果是查找队头元素的函数,省去这句代码即可
Q.front=(Q.front+1)%maxsize;
//删除成功
Q.tag=0;
return true;
}
队列中的元素个数:(rear-front+maxsize)%maxsize
队列的链式实现
1、定义
//链式队列的定义
typedef struct LinkNode{
int date;
struct LinkNode *next;
}LinkNode;
typedef struct{
LinkNode *front,*rear;
}LinkQueue;
2、带头结点初始化和判空
//链式队列的初始化——带头结点
void InitLinkQueue(LinkQueue &Q){
//申请头结点,且头尾指针都指向头结点
Q.front=Q.rear=(LinkNode *)malloc(sizeof(LinkNode*)*1);
//头结点的next为NULL
Q.front->next=NULL;
}
//判空
bool Empty(LinkQueue Q){
if(Q.front->next==NULL)//或Q.rear==Q.front
return true;
else
return false;
}
3、不带头结点的初始化和判空
//链式队列的初始化——不带头结点
void InitLinkQueue(LinkQueue &Q){
Q.front=Q.rear=NULL;
}
//判空
bool Empty(LinkQueue Q){
if(Q.front==NULL)
return true;
else
return false;
}
4、入队(带头结点和不带头结点)
//链式队列入队——带头结点
void EnQueue(LinkQueue &Q,int e){
//申请结点存放数据e
LinkNode *s=(LinkNode *)malloc(sizeof(LinkNode)*1);
s->data=e;
//链接链表
s->next=NULL;
Q.rear->next=s;
//移动尾指针
Q.rear=s;
}
//链式队列入队——不带头结点
void EnQueue(LinkQueue &Q,int e){
//申请结点存放数据e
LinkNode *s=(LinkNode *)malloc(sizeof(LinkNode)*1);
s->data=e;
//链接链表
s->next=NULL;
//入队元素为队列第一个元素时
if(Q.front==NULL){
Q.front=s;
Q.rear=s;
}
else{
Q.rear->next=s;
Q.rear=s;
}
}
5、出队(带头结点和不带头结点)
//链式队列出队——带头结点
bool DeLinkQueue(LinkQueue &Q,int &x){
//队空
if(Q.front==Q.rear)
return false;
LinkNode *p=Q.front
x=Q.front->data;
//修改头结点
Q.front->next=p->next;
//如果出队的元素是队列中最后一个元素
if(Q.rear=p)
Q.rear=Q.front;
free(p);
return true;
}
//链式队列出队—不带头结点
bool DeLinkQueue(LinkQueue &Q,int &x){
//队空
if(Q.front==NULL)
return false;
LinkNode *p=Q.front
x=Q.front->data;
//修改头结点
Q.front=p->next;
//如果出队的元素是队列中最后一个元素
if(Q.rear=p)
Q.rear=Q.front=NULL;
free(p);
return true;
}