先上图,以图服人:
上代码:
头文件LinkQueue.h:
/*LinkQueue.h*/
#ifndef LINKQUEUE_H_INCLUDED
#define LINKQUEUE_H_INCLUDED
#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>
#include <stdbool.h>
#include <time.h>
#include <windows.h>
typedef int LQElementType;
typedef struct Node
{
LQElementType Data;
struct Node *Next;
}LNode,*PNode;
typedef struct LinkQueue
{
LNode *Front,*Rear;
}LQueue,*PQueue;
PQueue InitiateQueue(PQueue LQ);/*初始化队列*/
void DestroyQueue(PQueue LQ);/*销毁队列*/
void Display(PQueue LQ);/*打印队列:边出队边打印队首元素,不推荐使用*/
void ShowQueue(PQueue LQ);/*打印队列2*/
bool ClearQueue(PQueue LQ);/*清空队列*/
bool EmptyQueue(PQueue LQ);/*判断队列是否为空*/
bool EnQueue(PQueue LQ,LQElementType Value);/*队尾入队*/
bool DeQueue(PQueue LQ,LQElementType *Tmp);/*队首出队*/
bool GetFront(PQueue LQ,LQElementType *Tmp);/*获取队首元素*/
int QueueSize(PQueue LQ);/*返回队列长度*/
#endif // LINKQUEUE_H_INCLUDED
源文件test.c:
/*test.c*/
/*
Name:纯C语言实现链式队列的相关操作
Copyright:2018
Author:刁肥宅
Date: 06/08/18 17:49
Description:一切尽在注释中!
*/
#include "LinkQueue.h"
int main()
{
srand(time(NULL));
LQueue *LQ = (LQueue *)malloc(sizeof(LQueue)),*LQ2 = NULL;
int Value,i,QueueLength,Line = 0,FirstKey = -1;
int DeQueueFrequency = 0,EnQueueFrequency = 0,ChoosingKey,RandomEnQueueValue = 0,RandomOperatingSize = 0;
LQ = InitiateQueue(LQ);
LQ2 = LQ;
QueueLength = rand() % 1000 + 1;
for(i = 0;i < QueueLength;i ++)
{
Value = rand() % 10000 + 1;
/*Value = 100;*/
if(EnQueue(LQ,Value))
continue;
else
break;
}
for(i = 0;i < RandomOperatingSize;i ++)
{
ChoosingKey = rand() % 2 + 0;
if(!ChoosingKey)
{
if(DeQueue(LQ2,&FirstKey))
DeQueueFrequency ++;
/*else
continue;*/
}
else
{
RandomEnQueueValue = rand() % 10000 + 1;
if(EnQueue(LQ2,RandomEnQueueValue))
EnQueueFrequency ++;
}
}
int n = QueueSize(LQ);
printf("QueueSize() = %d\n",n);
ShowQueue(LQ);
printf("\n\n");
/*Display(LTmp);*/
DeQueue(LQ,&FirstKey);
printf("FirstKey = %d\n",FirstKey);
if(GetFront(LQ,&FirstKey))
printf("After DeQueue,FirstKey = %d\n\n",FirstKey);
else
printf("GetFront Error.\n");
printf("EnQueueFrequency = %d,DeQueueFrequency = %d\n",EnQueueFrequency,DeQueueFrequency);
ClearQueue(LQ);
int n2 = QueueSize(LQ);
printf("QueueSize() = %d\n",n2);
DestroyQueue(LQ);
int n1 = QueueSize(LQ);
printf("QueueSize() = %d\n",n1);
if(LQ->Front->Next == NULL)
printf("DestroyQueue Succeed\n");
else
{
if(EmptyQueue(LQ))
printf("Empty\n");
else
printf("Not Empty\n");
}
/*
LQ2 = InitiateQueue(LQ2);
RandomOperatingSize = rand() % 1000 + 1;
for(i = 0;i < RandomOperatingSize;i ++)
{
Value = rand() % 1000 + 1;
if(EnQueue(LQ2,Value))
continue;
else
break;
}
for(i = 0;i < RandomOperatingSize;i ++)
{
ChoosingKey = rand() % 2 + 0;
if(!ChoosingKey)
{
if(DeQueue(LQ,&FirstKey))
DeQueueFrequency ++;
else
continue;
}
else
{
RandomEnQueueValue = rand() % 10000 + 1;
if(EnQueue(LQ,RandomEnQueueValue))
EnQueueFrequency ++;
}
}
n2 = QueueSize(LQ2);
printf("QueueSize() = %d\n",n2);
if(GetFront(LQ2,&FirstKey))
printf("Key = %d\n\n",FirstKey);
else
printf("GetFront Error.\n");
ShowQueue(LQ2);
printf("EnQueueFrequency = %d,DeQueueFrequency = %d\n",EnQueueFrequency,DeQueueFrequency);
*/
printf("\n");
printf("The screen will be closed in 60 seconds.\n");
Sleep(1000 * 60);
return 0;
}
PQueue InitiateQueue(PQueue LQ)
{
LQ->Front = LQ->Rear = (LNode *)malloc(sizeof(LNode));
/*LQ->Front = LQ->Rear;*/
if(!LQ->Front)
{
printf("Initiate failed.\n");
exit(EXIT_FAILURE);
}
LQ->Front->Next = NULL;
return LQ;
}
bool EmptyQueue(PQueue LQ)
{
return LQ->Front == LQ->Rear;
}
bool EnQueue(PQueue LQ,LQElementType Value)
{
LNode *QueueNodeTmp = (LNode *)malloc(sizeof(LNode));
QueueNodeTmp->Next = NULL;
QueueNodeTmp->Data = Value;
/*if(QueueEmpty(LQ))*/
if(!LQ->Rear)
LQ->Front = LQ->Rear = QueueNodeTmp;
else
{
LQ->Rear->Next = QueueNodeTmp;
LQ->Rear = QueueNodeTmp;
}
return true;
}
bool DeQueue(PQueue LQ,LQElementType *Tmp)
{
if(!LQ->Front)
return false;
/*
LNode *NodeTmp = (LNode *)malloc(sizeof(LNode));
NodeTmp = LQ->Front;
*Tmp = LQ->Front->Next->Data;*/
LNode *NodeTmp = LQ->Front;
*Tmp = NodeTmp->Next->Data;
/*
上面这句话我原来写作:
*Tmp = LQ->Front->Data;
等价于:
*Tmp = NodeTmp->Data;
导致 Display 函数 调用 DeQueue 函数时,第一个打印出来的总是随机数值。
原因:
第一次加载数据没有走EnQueue 函数的 if 条件语句,然后 LQ->Front->Data 就没值(不指向Next无
法识别数据域)
症结:不理解指针、队列的某些基本概念
*/
LQ->Front = NodeTmp->Next;
if(NodeTmp == LQ->Rear)
LQ->Front = LQ->Rear;
free(NodeTmp);
if(!LQ->Front)
LQ->Rear = NULL;
/*NodeTmp = NULL;*/
return true;
}
void DestroyQueue(PQueue LQ)
{
LNode *Tmp = (LNode *)malloc(sizeof(LNode));
/*solution 1:*/
while(LQ->Front != LQ->Rear)
{
Tmp = LQ->Front->Next;
free(LQ->Front);
LQ->Front = Tmp;
}
/*solution 2(badly function):
while(LQ->Front != NULL)
{
Tmp = LQ->Front;
LQ->Front = Tmp->Next;
free(Tmp);
}
*/
LQ->Front->Next = LQ->Rear->Next = NULL;
/*LQ->Front = LQ->Rear;*/
}
bool ClearQueue(PQueue LQ)
{
if(EmptyQueue(LQ))
return false;
LQ->Front = LQ->Rear;
return true;
}
void Display(PQueue LQ)
{
int x = -1,Line = 0;
if(LQ->Front == LQ->Rear)
{
printf("Empty Queue.\n");
exit(EXIT_FAILURE);
}
while(LQ->Front != LQ->Rear)
{
/*printf("%-6d",LQ->Front->Data);
LQ = LQ->Front;*/
if(DeQueue(LQ,&x))
{
printf("%-6d",x);
++ Line;
if(Line % 10 ==0)
printf("\n");
}
}
}
void ShowQueue(PQueue LQ)
{
/*
LNode *Tmp = (LNode *)malloc(sizeof(LNode));
Tmp = LQ->Front->Next;
*/
LNode *Tmp = LQ->Front->Next;
int Line = 0;
while(Tmp)
{
printf("%-6d",Tmp->Data);
++ Line;
if(Line % 10 == 0)
printf("\n");
Tmp = Tmp->Next;
}
}
bool GetFront(PQueue LQ,LQElementType *Tmp)
{
if(!LQ->Front)
return false;
*Tmp = LQ->Front->Next->Data;
return true;
}
int QueueSize(PQueue LQ)
{
if(!LQ->Front)
return -1;
LNode *Tmp = LQ->Front;
int ID = 0;
while(LQ->Rear != Tmp)
{
Tmp = Tmp->Next;
++ ID;
}
return ID;
}