在C语言中,.和->运算符用于访问结构体的成员变量。它们之间的区别在于:.运算符用于访问结构体变量的成员。->运算符用于访问结构体指针变量的成员
1a(rear指向队尾元素后一位,判空判满时牺牲一个存储单元)
首先我们考虑1a的情况下在牺牲一个存储单元rear指向队尾元素后一个位置该怎么实现队列的基本操作,当rear指向队尾元素的后一位时,队列的实现需要牺牲一个存储单元来区分队列是空还是满
#include <stdio.h>
#include <stdlib.h>
#define MaxSize 10 // 定义队列中元素的最大个数
typedef struct {
int data[MaxSize]; // 用静态数组存放队列元素
int front, rear; // 队头指针和队尾指针
} SqQueue;
// 初始化队列
void InitQueue(SqQueue* Q) {
Q->front = Q->rear = 0; // 初始时队头、队尾指针指向0
}
// 判断队列是否为空
bool QueueEmpty(SqQueue* Q) {
return Q->front == Q->rear; // 判空条件:队头指针等于队尾指针
}
// 判断队列是否已满
bool QueueFull(SqQueue* Q) {
return (Q->rear + 1) % MaxSize == Q->front; // 判满条件:队尾指针后移一位后等于队头指针
}
// 入队
bool EnQueue(SqQueue* Q, int x) {
if (QueueFull(Q)) { // 判断队满
return false; // 队满报错
} else {
Q->data[Q->rear] = x; // 新元素插入队尾
Q->rear = (Q->rear + 1) % MaxSize; // 队尾指针后移
return true;
}
}
// 出队(删除一个队头元素,并用x返回)
bool DeQueue(SqQueue* Q, int* x) {
if (QueueEmpty(Q)) { // 判断队空
return false; // 队空则报错
} else {
Q->front = (Q->front + 1) % MaxSize; // 队头指针后移
*x = Q->data[Q->front]; // 获取队头元素
return true;
}
}
// 获得队头元素的值,用x返回
bool GetHead(SqQueue* Q, int* x) {
if (QueueEmpty(Q)) { // 判断队空
return false; // 队空则报错
} else {
*x = Q->data[Q->front]; // 获取队头元素
return true;
}
}
在这个实现中,队列满的条件是队尾指针后移一位后等于队头指针。这意味着队列的实际容量是MaxSize - 1
,因为一个存储单元被用来区分队列是空还是满。
2a(rear指向队尾元素,判空判满时牺牲一个存储单元)
当rear指向队尾元素时,队列的实现不需要牺牲额外的存储单元来区分队列是空还是满。在这种情况下,队列的实际容量就是MaxSize
,因为所有的存储单元都可以用来存储元素。
#include <stdio.h>
#include <stdlib.h>
#define MaxSize 10 // 定义队列中元素的最大个数
typedef struct {
int data[MaxSize]; // 用静态数组存放队列元素
int front, rear; // 队头指针和队尾指针
} SqQueue;
// 初始化队列
void InitQueue(SqQueue* Q) {
// 初始时队头指针指向0
// 队尾指针指向数组尾元素
Q->front = 0;
Q->rear = MaxSize - 1;
}
// 判断队列是否为空
bool QueueEmpty(SqQueue* Q) {
if (Q->rear == Q->front) { // 判空条件
return true;
} else {
return false;
}
}
// 判断队列是否已满
bool QueueFull(SqQueue* Q) {
if ((Q->rear + 1) % MaxSize == Q->front) { // 判满条件
return true;
} else {
return false;
}
}
// 入队
bool EnQueue(SqQueue* Q, int x) {
if (QueueFull(Q)) { // 判断队满
return false; // 队满报错
} else {
Q->rear = (Q->rear + 1) % MaxSize; // 队尾指针后移
Q->data[Q->rear] = x; // 新元素插入队尾
return true;
}
}
// 出队(删除一个队头元素,并用x返回)
bool DeQueue(SqQueue* Q, int* x) {
if (QueueEmpty(Q)) { // 判断队空
return false; // 队空则报错
} else {
Q->front = (Q->front + 1) % MaxSize; // 队头指针后移
*x = Q->data[Q->front]; // 获取队头元素
return true;
}
}
// 获得队头元素的值,用x返回
bool GetHead(SqQueue* Q, int* x) {
if (QueueEmpty(Q)) { // 判断队空
return false; // 队空则报错
} else {
*x = Q->data[(Q->front + 1) % MaxSize]; // 获取队头元素
return true;
}
}
在这个实现中,队列满的条件是队尾指针后移一位后等于队头指针。这意味着队列的实际容量是MaxSize
,因为所有的存储单元都可以用来存储元素 ,与1a的相比主要改变了入队和初始化的操作,入队的时候,rear需要先往后一位,再接受新的数据。
1b(rear指向队尾元素后一位,增加size变量记录长度)
#include <stdio.h>
#include <stdlib.h>
#define MaxSize 10 // 定义队列中元素的最大个数
typedef struct {
int data[MaxSize]; // 用静态数组存放队列元素
int front, rear; // 队头指针和队尾指针
int size;//增加一个size记录队列的长度
} SqQueue;
// 初始化队列
void InitQueue(SqQueue* Q) {
// 初始时队头、队尾指针指向0
Q->rear = Q->front = 0;
Q->size = 0;
}
// 判断队列是否为空
bool QueueEmpty(SqQueue Q) {
if (Q->size == 0) { // 判空条件
return true;
}
else {
return false;
}
bool QueueFull(SqQueue Q) {
if (Q->size==MaxSize) { // 判满条件
return true;
}
else {
return false;
}
}
// 入队
bool EnQueue(SqQueue* Q, int x) {
if (QueueFull(*Q)) { // 判断队满
return false; // 队满报错
}
else {
Q->data[Q->rear] = x; // 新元素插入队尾
Q->rear = (Q->rear + 1) % MaxSize; // 队尾指针加1取模,队尾指针后移
Q->size = Q->size + 1; // 队列长度加1
return true;
}
}
// 出队(删除一个队头元素,并用x返回)
bool DeQueue(SqQueue* Q, int* x) {
if (QueueEmpty(*Q)) { // 判断队空
return false; // 队空则报错
}
else {
*x = Q->data[Q->front];
Q->front = (Q->front + 1) % MaxSize; // 队头指针后移
Q->size = Q->size - 1; // 队列长度减1
return true;
}
}
// 获得队头元素的值,用x返回
bool GetHead(SqQueue Q, int* x) {
if (QueueEmpty(*Q)) { // 判断队空
return false; // 队空则报错
}
else {
*x = Q.data[Q.front];
return true;
}
}
2b(rear指向队尾元素,增加size变量记录长度)
#include <stdio.h>
#include <stdlib.h>
#define MaxSize 10 // 定义队列中元素的最大个数
typedef struct {
int data[MaxSize]; // 用静态数组存放队列元素
int front, rear; // 队头指针和队尾指针
int size;//增加一个size记录队列的长度
} SqQueue;
// 初始化队列
void InitQueue(SqQueue* Q) {
// 初始时队头、队尾指针指向
Q->front = 0;
Q->rear = MaxSize - 1;
Q->size = 0;
}
// 判断队列是否为空
bool QueueEmpty(SqQueue Q) {
if (Q->size == 0) { // 判空条件
return true;
}
else {
return false;
}
bool QueueFull(SqQueue Q) {
if (Q->size==MaxSize) { // 判满条件
return true;
}
else {
return false;
}
}
// 入队
bool EnQueue(SqQueue* Q, int x) {
if (QueueFull(*Q)) { // 判断队满
return false; // 队满报错
}
else {
Q->rear = (Q->rear + 1) % MaxSize; // 队尾指针加1取模,队尾指针后移
Q->data[Q->rear] = x; // 新元素插入队尾
Q->size = Q->size + 1; // 队列长度加1
return true;
}
}
// 出队(删除一个队头元素,并用x返回)
bool DeQueue(SqQueue* Q, int* x) {
if (QueueEmpty(*Q)) { // 判断队空
return false; // 队空则报错
}
else {
*x = Q->data[Q->front];
Q->front = (Q->front + 1) % MaxSize; // 队头指针后移
Q->size = Q->size - 1; // 队列长度减1
return true;
}
}
// 获得队头元素的值,用x返回
bool GetHead(SqQueue Q, int* x) {
if (QueueEmpty(*Q)) { // 判断队空
return false; // 队空则报错
}
else {
*x = Q.data[Q.front];
return true;
}
}
3a(rear指向队尾元素后一位,判空判满时添加一个tag标签标记)
#include <stdio.h>
#include <stdlib.h>
#define MaxSize 10 // 定义队列中元素的最大个数
typedef struct {
int data[MaxSize]; // 用静态数组存放队列元素
int front, rear; // 队头指针和队尾指针
int tag;//tag标签用于标记,0=出队,1=入队
} SqQueue;
// 初始化队列
void InitQueue(SqQueue* Q) {
Q->front = Q->rear = 0; // 初始时队头、队尾指针指向0
Q->tag = 0;
}
// 判断队列是否为空
bool QueueEmpty(SqQueue* Q) {
return (Q->front == Q->rear&&Q->tag==0); // 判空条件:队头指针等于队尾指针
}
// 判断队列是否已满
bool QueueFull(SqQueue* Q) {
return ((Q->rear + 1) % MaxSize == Q->front&&Q->tag==1); // 判满条件:队尾指针后移一位后等于队头指针
}
// 入队
bool EnQueue(SqQueue* Q, int x) {
if (QueueFull(Q)) { // 判断队满
return false; // 队满报错
}
else {
Q->data[Q->rear] = x; // 新元素插入队尾
Q->rear = (Q->rear + 1) % MaxSize; // 队尾指针后移
Q->tag = 1;//入队后tag变为1;
return true;
}
}
// 出队(删除一个队头元素,并用x返回)
bool DeQueue(SqQueue* Q, int* x) {
if (QueueEmpty(Q)) { // 判断队空
return false; // 队空则报错
}
else {
Q->front = (Q->front + 1) % MaxSize; // 队头指针后移
*x = Q->data[Q->front]; // 获取队头元素
Q->tag = 1;//出队后tag变为1;
return true;
}
}
// 获得队头元素的值,用x返回
bool GetHead(SqQueue* Q, int* x) {
if (QueueEmpty(Q)) { // 判断队空
return false; // 队空则报错
}
else {
*x = Q->data[Q->front]; // 获取队头元素
return true;
}
}
3b(rear指向队尾元素,判空判满时添加一个tag标签标记)
#include <stdio.h>
#include <stdlib.h>
#define MaxSize 10 // 定义队列中元素的最大个数
typedef struct {
int data[MaxSize]; // 用静态数组存放队列元素
int front, rear; // 队头指针和队尾指针
int tag;//tag标签用于标记,0=出队,1=入队
} SqQueue;
// 初始化队列
void InitQueue(SqQueue* Q) {
Q->front = 0//初始时队头指针指向队头元素
Q->rear = MaxSize-1;//初始时队尾指针指向队尾元素
Q->tag = 0;
}
// 判断队列是否为空
bool QueueEmpty(SqQueue* Q) {
return (Q->front == Q->rear && Q->tag == 0); // 判空条件:队头指针等于队尾指针
}
// 判断队列是否已满
bool QueueFull(SqQueue* Q) {
return ((Q->rear + 1) % MaxSize == Q->front && Q->tag == 1); // 判满条件:队尾指针后移一位后等于队头指针
}
// 入队
bool EnQueue(SqQueue* Q, int x) {
if (QueueFull(Q)) { // 判断队满
return false; // 队满报错
}
else {
Q->rear = (Q->rear + 1) % MaxSize; // 队尾指针后移
Q->data[Q->rear] = x; // 新元素插入队尾
Q->tag = 1;//入队后tag变为1;
return true;
}
}
// 出队(删除一个队头元素,并用x返回)
bool DeQueue(SqQueue* Q, int* x) {
if (QueueEmpty(Q)) { // 判断队空
return false; // 队空则报错
}
else {
Q->front = (Q->front + 1) % MaxSize; // 队头指针后移
*x = Q->data[Q->front]; // 获取队头元素
Q->tag = 1;//出队后tag变为1;
return true;
}
}
// 获得队头元素的值,用x返回
bool GetHead(SqQueue* Q, int* x) {
if (QueueEmpty(Q)) { // 判断队空
return false; // 队空则报错
}
else {
*x = Q->data[Q->front]; // 获取队头元素
return true;
}
}