一、队列简述
队列也是一种特殊的线性表,其特殊性在于队列的基本操作是线性表操作的一个子集。队列按“先进先出”的规则进行操作,故称其为操作受限的线性表。
1、队列的定义
队列(queue)是另一种操作受限的线性表,它只允许在表的一段插入元素,而在另一端删除元素。允许插入数据的一端称之为队尾(rear),允许删除数据的一端称之为队头(front)。向队列中插入新的数据元素称之为入队,新的数据元素入队后就称为队列的队尾元素。从队列中删除队头元素称之为出队,队头元素出队后,其后继数据元素称为新的队头元素,
2、队列的特点
由于队列的插入、删除操作分别在表的两端进行,所以每个数据元素出队的次序必然就是他们进队的次序。因此,队列具有“先进先出”的特性。
3、图解队列
二、顺序循环队列
为什么要做顺序循环队列呢?一般的队列是这样的:
当队列中的红色部分出队后,其所在的空间等于是浪费掉了,队列只剩下后面的空间,而顺序循环队列是这样的:
当队头front出队后,新的队头指向了红色箭头的位置,而原来队头的位置可以在之后被新入队的元素占据,这样空间的利用程度会提高。
#pragma once
#define QUEUE_INT_SIZE 10
typedef int ElemType;
typedef struct Queue
{
ElemType *base;
int head;
int rear;
}SqQueue;
void InitQueue(SqQueue *que);
int EmptyQueue(SqQueue *que);
int FullQueue(SqQueue *que);
int PushQueue(SqQueue *que, ElemType val);
int GetHead(SqQueue *que, ElemType *val);
int PopQueue(SqQueue *que, ElemType *val);
void ClearQueue(SqQueue *que);
void DestroyQueue(SqQueue *que);
#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#include "queue.h"
static void DeterPointIsNULL(SqQueue *que)
{
assert(que != NULL);
if (que == NULL)
{
exit(0);
}
}
void InitQueue(SqQueue *que)
{
DeterPointIsNULL(que);
que->base = (ElemType *)malloc(sizeof(ElemType)* QUEUE_INT_SIZE);
que->head = 0;
que->rear = 0;
}
int EmptyQueue(SqQueue *que)
{
DeterPointIsNULL(que);
if (que->head == que->rear)
{
return 1;
}
return 0;
}
int FullQueue(SqQueue *que)
{
DeterPointIsNULL(que);
if (que->head == (que->rear + 1) % QUEUE_INT_SIZE)
{
return 1;
}
return 0;
}
int PushQueue(SqQueue *que, ElemType val)
{
DeterPointIsNULL(que);
if (FullQueue(que))
{
printf("Que is Full, Push Fail\n");
return 0;
}
que->base[que->rear] = val;
que->rear = (que->rear + 1) % QUEUE_INT_SIZE;
return 1;
}
int GetHead(SqQueue *que, ElemType *val)
{
DeterPointIsNULL(que);
if (EmptyQueue(que))
{
printf("Que is Empty, GetHead Fail\n");
return 0;
}
*val = que->base[que->head];
return 1;
}
int PopQueue(SqQueue *que, ElemType *val)
{
DeterPointIsNULL(que);
if (!GetHead(que, val))
{
return 0;
}
que->head = (que->head + 1) % QUEUE_INT_SIZE;
}
void ClearQueue(SqQueue *que)
{
DeterPointIsNULL(que);
que->head = 0;
que->rear = 0;
}
void DestroyQueue(SqQueue *que)
{
DeterPointIsNULL(que);
free(que->base);
que->base = NULL;
que->head = 0;
que->rear = 0;
}