C语言队列的数组实现(源码笔记)
queue.h
typedef int ElementType;
/* START: fig3_57.txt */
#ifndef _Queue_h
#define _Queue_h
struct QueueRecord;
typedef struct QueueRecord *Queue;
int IsEmpty(Queue Q);
int IsFull(Queue Q);
Queue CreateQueue(int MaxElements);
void DisposeQueue(Queue Q);
void MakeEmpty(Queue Q);
void Enqueue(ElementType X, Queue Q);
ElementType Front(Queue Q);
void Dequeue(Queue Q);
ElementType FrontAndDequeue(Queue Q);
#endif /* _Queue_h */
/* END */
queue.c
#include "queue.h"
#include "fatal.h"
#include <stdlib.h>
#define MinQueueSize ( 5 ) // 队列中存储数据的数组最小也得能存5个
struct QueueRecord
{
int Capacity; // 容量
int Front; // 队列头
int Rear; // 队列尾
int Size; // 尺寸
ElementType *Array;
};
/* START: fig3_58.txt */
int
IsEmpty(Queue Q)
{
return Q->Size == 0;
}
/* END */
int
IsFull(Queue Q)
{
return Q->Size == Q->Capacity; // 这里这样判断的原因是队列可以越过Capacity - 1这个索引,并且判断的标准是Size,所以是循环数组
}
Queue
CreateQueue(int MaxElements)
{
Queue Q;
/* 1*/ if (MaxElements < MinQueueSize)
/* 2*/ Error("Queue size is too small");
/* 3*/ Q = malloc(sizeof(struct QueueRecord));
/* 4*/ if (Q == NULL)
/* 5*/ FatalError("Out of space!!!");
/* 6*/ Q->Array = malloc(sizeof(ElementType) * MaxElements);
/* 7*/ if (Q->Array == NULL)
/* 8*/ FatalError("Out of space!!!");
/* 9*/ Q->Capacity = MaxElements;
/*10*/ MakeEmpty(Q);
/*11*/ return Q;
}
/* START: fig3_59.txt */
void
MakeEmpty(Queue Q)
{
Q->Size = 0; // 初始元素个数为0
Q->Front = 1; // 头节点初始化为1
Q->Rear = 0; // 尾节点初始化为0
}
/* END */
void
DisposeQueue(Queue Q)
{
if (Q != NULL)
{
free(Q->Array);
free(Q);
}
}
/* START: fig3_60.txt */
// 这两个是入队的例程
static int
Succ(int Value, Queue Q)
{
if (++Value == Q->Capacity)
Value = 0;
return Value;
}
void
Enqueue(ElementType X, Queue Q)
{
if (IsFull(Q))
Error("Full queue");
else
{
Q->Size++;
Q->Rear = Succ(Q->Rear, Q);
Q->Array[Q->Rear] = X; // 这里是向队尾追加元素
}
}
/* END */
// 返回队列的首元素
ElementType
Front(Queue Q)
{
if (!IsEmpty(Q))
return Q->Array[Q->Front];
Error("Empty queue");
return 0; /* Return value used to avoid warning */
}
// 出队
void
Dequeue(Queue Q)
{
if (IsEmpty(Q))
Error("Empty queue");
else
{
Q->Size--;
Q->Front = Succ(Q->Front, Q); // 因为遵循先进先出原则,所以队头要这样处理
}
}
// 在出队的同时返回该元素
ElementType
FrontAndDequeue(Queue Q)
{
ElementType X = 0;
if (IsEmpty(Q))
Error("Empty queue");
else
{
Q->Size--;
X = Q->Array[Q->Front];
Q->Front = Succ(Q->Front, Q);
}
return X;
}
testque.c(main.c)
#include <stdio.h>
#include "queue.h"
int main()
{
Queue Q;
int i;
Q = CreateQueue(12);
// 先入队10个元素,从0~9
for (i = 0; i < 10; i++)
Enqueue(i, Q);
// 打印队列里面的元素,打印完之后出队
while (!IsEmpty(Q))
{
printf("%d\n", Front(Q));
Dequeue(Q);
}
// 再次插入10个元素
for (i = 0; i < 10; i++)
Enqueue(i, Q);
// 打印
while (!IsEmpty(Q))
{
printf("%d\n", Front(Q));
Dequeue(Q);
}
DisposeQueue(Q);
return 0;
}
fatal.h
#include <stdio.h>
#include <stdlib.h>
#define Error(Str) FatalError( Str )
#define FatalError(Str) fprintf( stderr, "%s\n", Str ), exit( 1 )
运行结果: