用迴圈單鏈表來表示佇列
阿新 • • 發佈:2019-01-27
假設用一個迴圈單鏈表來表示佇列,並且只設置一個指標rear指向隊尾結點,但不設定頭指標,設計出相應的初始化、入隊、出隊和判斷佇列是否為空的演算法。
方法一:使用不帶頭結點的迴圈單鏈表
1.1)隊空條件 rear==NULL
1.2) 入隊, 在*rear結點之後插入結點,並讓rear指向該結點
1.3) 出隊,刪除*rear結點之後的一個結點
如圖(1)所示:
程式碼如下:
/*-------------一、不帶頭結點的迴圈單鏈表示佇列------------------------*/
void InitQu(QNode *&rear){
rear=NULL;
}
//入隊
void EnQu(QNode *&rear,ElemType x){
QNode *s;
s=(QNode *)malloc(sizeof(QNode));
s->data=x;
if (rear==NULL) //佇列為空
{
s->next=s;
rear=s;
}
else{ //佇列不為空
s->next=rear->next;
rear-> next=s;
rear=s;
}
}
//出隊
int DeQu(QNode *&rear,ElemType &x){
QNode *q;
if(rear==NULL)
return 0;
else if (rear->next == rear)
{
x=rear->data;
free(rear);
rear=NULL;
}
else{
q=rear->next;
x=q->data;
rear-> next=q->next;
free(q);
}
return 1;
}
//判斷佇列是否為空
int QuEmpty(QNode *rear){
return (rear==NULL);
}
方法二:使用帶頭結點的迴圈單鏈表
2.1) 隊空條件 rear->next == rear
2.2) 入隊, 在*rear結點之後插入結點並讓rear指向該結點
2.3) 出隊, 刪除rear->next結點之後的一個結點
如圖(2)所示:
程式碼如下:
void InitQu1(QNode *&rear){
rear=(QNode *)malloc(sizeof(QNode));
rear->next=rear;
}
//進隊
void EnQu1(QNode *&rear,ElemType x){
QNode *s;
s=(QNode *)malloc(sizeof(QNode));
s->next=NULL;
s->data=x;
s->next=rear->next;
rear->next=s;
rear=s;
}
//出隊
int DeQu1(QNode *&rear,ElemType &x){
QNode *q;
if(rear->next==rear)
return 0;
else if(rear->next->next==rear){
x=rear->data;
q=rear->next;
q->next=q;
free(rear);
rear=q;
return 1;
}
else{
q=rear->next->next;
x=q->data;
rear->next->next=q->next;
free(q);
return 1;
}
}
int QuEmpty1(QNode *rear){
return (rear->next==rear);
}
//duiLie.cpp
完整程式碼如下:
#include <stdio.h>
#include <malloc.h>
typedef int ElemType;
typedef struct qnode{ //資料結點
ElemType data;
struct qnode *next;
}QNode;
typedef struct{ //鏈隊定義
QNode *front;
QNode *rear;
}LiQueue;
/*-------------一、不帶頭結點的迴圈單鏈表示佇列---------------*/
void InitQu(QNode *&rear){
rear=NULL;
}
//入隊
void EnQu(QNode *&rear,ElemType x){
QNode *s;
s=(QNode *)malloc(sizeof(QNode));
s->data=x;
if (rear==NULL) //佇列為空
{
s->next=s;
rear=s;
}
else{ //佇列不為空
s->next=rear->next;
rear->next=s;
rear=s;
}
}
//出隊
int DeQu(QNode *&rear,ElemType &x){
QNode *q;
if(rear==NULL)
return 0;
else if (rear->next == rear)
{
x=rear->data;
free(rear);
rear=NULL;
}
else{
q=rear->next;
x=q->data;
rear->next=q->next;
free(q);
}
return 1;
}
//判斷佇列是否為空
int QuEmpty(QNode *rear){
return (rear==NULL);
}
/*-------------------二、用帶頭結點的迴圈單鏈表表示佇列------------------*/
void InitQu1(QNode *&rear){
rear=(QNode *)malloc(sizeof(QNode));
rear->next=rear;
}
//進隊
void EnQu1(QNode *&rear,ElemType x){
QNode *s;
s=(QNode *)malloc(sizeof(QNode));
s->next=NULL;
s->data=x;
s->next=rear->next;
rear->next=s;
rear=s;
}
//出隊
int DeQu1(QNode *&rear,ElemType &x){
QNode *q;
if(rear->next==rear)
return 0;
else if(rear->next->next==rear){
x=rear->data;
q=rear->next;
q->next=q;
free(rear);
rear=q;
return 1;
}
else{
q=rear->next->next;
x=q->data;
rear->next->next=q->next;
free(q);
return 1;
}
}
int QuEmpty1(QNode *rear){
return (rear->next==rear);
}
//不帶頭結點的迴圈單鏈表輸出
void DispQueueR(QNode *&rear){
if(rear==NULL)
return;
QNode *p=rear->next;
do{
printf("%d ",p->data);
p=p->next;
}while(p!=rear->next);
printf("\n");
}
//帶頭結點的迴圈單鏈表輸出
void DispQueueR2(QNode *&rear){
if (rear->next == rear)
return;
QNode *q=rear->next->next;
while(q!=rear){
printf("%d ",q->data);
q=q->next;
}
if (q==rear)
{
printf("%d ",q->data);
}
printf("\n");
}
void main()
{
QNode *p;
//不帶頭結點的迴圈單鏈表
// InitQu(p);
// int i=0;
// for (i=1;i<10;i++)
// {
// EnQu(p,i*i-1);
// }
// DispQueueR(p);
//帶頭結點的迴圈單鏈表
InitQu1(p);
int j=0;
for (j=1;j<10;j++)
{
EnQu1(p,j*j-1);
}
DispQueueR2(p);
}
效果如下: