【数据结构】线性表(八)队列:顺序队列及其基本操作(初始化、判空、判满、入队、出队、存取队首元素)

news2024/10/6 21:30:19

文章目录

  • 一、队列
    • 1. 定义
    • 2. 基本操作
  • 二、顺序队列
    • 0. 顺序表
    • 1. 头文件和常量
    • 2. 队列结构体
    • 3. 队列的初始化
    • 4. 判断队列是否为空
    • 5. 判断队列是否已满
    • 6. 入队
    • 7. 出队
    • 8. 存取队首元素
    • 9. 主函数
    • 10. 代码整合

  堆栈Stack 和 队列Queue是两种非常重要的数据结构,两者都是特殊的线性表:

  • 对于堆栈,所有的插入和删除(以至几乎所有的存取)都是在表的同一端进行;
  • 对于队列,所有的插入都是在表的一端进行,所有的删除(以至几乎所有的存取)都是在表的另一端进行。

一、队列

1. 定义

  队列是一种操作受限的线性表,对于它的所有插入都在表的一端进行,所有的删除(以至几乎所有的存取)都在表的另一端进行,且这些操作又都是按照先进先出(FIFO)的原则进行的。进行删除的一端称为队头(front),进行插入的一端称为队尾(rear)。没有元素的队列称为空队列(简称空队)。

在这里插入图片描述
  队列就像生活中排队购物,新来的人只能加入队尾(假设不允许插队),购物结束后先离开的总是队头(假设无人中途离队)。也就是说,先加入队列的成员总是先离开队列,因此队列被称为先进先出(First In First Out)的线性表,简称为FIFO表。如图,在空队列中依次加入元素a1,a2,a3,a4,a5,出队次序仍然是a1,a2,a3,a4,a5 .

2. 基本操作

  • 队列是受限的线性表,其基本操作包括

    • IsEmpty() : 判断队列是否为空;
    • isFull():判断队列是否为满;
    • enqueue() :向队尾添加元素(入队);
    • dequeue() :删除队首元素(出队);
    • peek():获取队首的元素值(存取);
  • 同普通线性表一样,队列也可以用顺序存储和链接存储两种方式来实现:

二、顺序队列

  用顺序存储方式实现的堆栈称为顺序队列

0. 顺序表

参考前文:顺序表及其基本操作

1. 头文件和常量

#include <stdio.h>
#define MAX_SIZE 100
  • 头文件stdio.h用于输入输出操作

  • 通过#define指令定义了一个常量MAX_SIZE,它表示顺序队列中数组的最大容量为100

2. 队列结构体

typedef struct {
    int data[MAX_SIZE]; // 存储队列元素的数组
    int front;          // 队头指针
    int rear;           // 队尾指针
} SequentialQueue;
  • 整型数组 data,用于存储队列元素;
  • frontrear 分别表示队头指针和队尾指针。

3. 队列的初始化

void initSequentialQueue(SequentialQueue* queue) {
    queue->front = -1;
    queue->rear = -1;
}

   initSequentialQueue 函数:初始化顺序队列,它将队头指针和队尾指针都设置为 -1,表示队列为空。

4. 判断队列是否为空

int isSequentialQueueEmpty(SequentialQueue* queue) {
    return queue->front == -1;
}

   isSequentialQueueEmpty 函数用于判断顺序队列是否为空:如果队头指针为 -1,表示队列为空,返回 1;否则返回 0。

5. 判断队列是否已满

int isSequentialQueueFull(SequentialQueue* queue) {
    return (queue->rear + 1) % MAX_SIZE == queue->front;
}

   isSequentialQueueFull 函数用于判断顺序队列是否已满。

6. 入队

void enqueueSequentialQueue(SequentialQueue* queue, int data) {
    if (isSequentialQueueFull(queue)) {
        printf("Error: Queue is full\n");
        return;
    }

    if (isSequentialQueueEmpty(queue)) {
        queue->front = 0;
        queue->rear = 0;
    } else {
        queue->rear = (queue->rear + 1) % MAX_SIZE;
    }

    queue->data[queue->rear] = data;
}
  • 判断队列是否已满
    • 如果已满则打印错误信息并返回;
    • 否则,根据队列是否为空进行不同的处理:
      • 如果队列为空,将队头指针和队尾指针都设置为 0;
      • 否则,将队尾指针移动到下一个位置,并将元素存储到队尾指针所指向的位置。

7. 出队

int dequeueSequentialQueue(SequentialQueue* queue) {
    if (isSequentialQueueEmpty(queue)) {
        printf("Error: Queue is empty\n");
        return -1;
    }

    int data = queue->data[queue->front];

    if (queue->front == queue->rear) {
        queue->front = -1;
        queue->rear = -1;
    } else {
        queue->front = (queue->front + 1) % MAX_SIZE;
    }

    return data;
}
  • 判断队列是否为空
    • 如果为空则打印错误信息并返回 -1;
    • 否则,取出队头元素,并根据队头指针是否等于队尾指针来判断队列是否为空:
      • 如果队列为空,将队头指针和队尾指针都设置为 -1;
      • 否则,将队头指针移动到下一个位置。

8. 存取队首元素

int peekSequentialQueue(SequentialQueue* queue) {
    if (isSequentialQueueEmpty(queue)) {
        printf("Error: Queue is empty\n");
        return -1;
    }

    return queue->data[queue->front];
}

   peekSequentialQueue 函数用于获取队首元素,即返回队列中队头指针所指向的元素的值。首先判断队列是否为空,如果为空则打印错误信息并返回 -1。

9. 主函数

int main() {
    SequentialQueue queue;
    initSequentialQueue(&queue);

    enqueueSequentialQueue(&queue, 10);
    enqueueSequentialQueue(&queue, 20);
    enqueueSequentialQueue(&queue, 30);

    printf("Peek: %d\n", peekSequentialQueue(&queue));

    printf("Dequeued: %d\n", dequeueSequentialQueue(&queue));
    printf("Dequeued: %d\n", dequeueSequentialQueue(&queue));

    printf("Peek: %d\n", peekSequentialQueue(&queue));

    enqueueSequentialQueue(&queue, 40);
    printf("Peek: %d\n", peekSequentialQueue(&queue));

    return 0;
}
  • 声明了一个 SequentialQueue 类型的变量 queue
  • 调用 initSequentialQueue 函数对其进行初始化
  • 调用 enqueueSequentialQueue 函数三次,依次将元素 10、20、30 入队
  • 使用 peekSequentialQueue 函数获取队首元素并打印
  • 调用 dequeueSequentialQueue 函数两次,依次将队列中的元素出队并打印
  • 再次使用 peekSequentialQueue 函数获取队首元素并打印
  • 调用 enqueueSequentialQueue 函数将元素 40 入队,并使用 peekSequentialQueue 函数获取队首元素并打印

在这里插入图片描述

10. 代码整合

#include <stdio.h>
#define MAX_SIZE 100

// 定义顺序队列
typedef struct {
    int data[MAX_SIZE]; // 存储队列元素的数组
    int front;          // 队头指针
    int rear;           // 队尾指针
} SequentialQueue;

// 初始化顺序队列
void initSequentialQueue(SequentialQueue* queue) {
    queue->front = -1;
    queue->rear = -1;
}

// 判断顺序队列是否为空
int isSequentialQueueEmpty(SequentialQueue* queue) {
    return queue->front == -1;
}

// 判断顺序队列是否已满
int isSequentialQueueFull(SequentialQueue* queue) {
    return (queue->rear + 1) % MAX_SIZE == queue->front;
}

// 入队
void enqueueSequentialQueue(SequentialQueue* queue, int data) {
    if (isSequentialQueueFull(queue)) {
        printf("Error: Queue is full\n");
        return;
    }

    if (isSequentialQueueEmpty(queue)) {
        queue->front = 0;
        queue->rear = 0;
    } else {
        queue->rear = (queue->rear + 1) % MAX_SIZE;
    }

    queue->data[queue->rear] = data;
}

// 出队
int dequeueSequentialQueue(SequentialQueue* queue) {
    if (isSequentialQueueEmpty(queue)) {
        printf("Error: Queue is empty\n");
        return -1;
    }

    int data = queue->data[queue->front];

    if (queue->front == queue->rear) {
        queue->front = -1;
        queue->rear = -1;
    } else {
        queue->front = (queue->front + 1) % MAX_SIZE;
    }

    return data;
}

// 获取队首元素
int peekSequentialQueue(SequentialQueue* queue) {
    if (isSequentialQueueEmpty(queue)) {
        printf("Error: Queue is empty\n");
        return -1;
    }

    return queue->data[queue->front];
}

// 示例代码的主函数
int main() {
    SequentialQueue queue;
    initSequentialQueue(&queue);

    enqueueSequentialQueue(&queue, 10);
    enqueueSequentialQueue(&queue, 20);
    enqueueSequentialQueue(&queue, 30);

    printf("Peek: %d\n", peekSequentialQueue(&queue));

    printf("Dequeued: %d\n", dequeueSequentialQueue(&queue));
    printf("Dequeued: %d\n", dequeueSequentialQueue(&queue));

    printf("Peek: %d\n", peekSequentialQueue(&queue));

    enqueueSequentialQueue(&queue, 40);
    printf("Peek: %d\n", peekSequentialQueue(&queue));

    return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1117568.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

论文浅尝 | Concept2Box:从双视图学习知识图谱的联合几何嵌入模型

笔记整理&#xff1a;张钊源&#xff0c;天津大学硕士&#xff0c;研究方向为知识图谱 链接&#xff1a;https://virtual2023.aclweb.org/paper_P4210.html 动机 知识图嵌入&#xff08;KGE&#xff09;已被广泛研究&#xff0c;用于嵌入大规模关系数据以满足许多现实世界的应用…

Spring Security总体架构介绍

参考&#xff1a;架构 :: Spring Security Reference (springdoc.cn) 一、过滤器 Spring Security 框架对 Servlet 请求的处理是基于过滤器机制。 容器会提前创建好FilterChain对每一个请求进行过滤&#xff0c;FilterChain中包含Filter 实例和 Servlet&#xff08;Spring MV…

编写后台登录滑动成功获取验证码 人机验证

vue-puzzle-vcode Vue 纯前端的拼图人机验证、右滑拼图验证 安装vue-puzzle-vcode npm install vue-puzzle-vcode --save使用vue-puzzle-vcode import Vcode from "vue-puzzle-vcode";<Vcode :show"isShow" success"onSuccess" close"…

ZooKeeper+HBase分布式集群环境搭建

安装版本&#xff1a;hadoop-2.10.1、zookeeper-3.4.12、hbase-2.3.1 一、zookeeper集群搭建与配置 1.下载zookeeper安装包 2.解压移动zookeeper 3.修改配置文件&#xff08;创建文件夹&#xff09; 4.进入conf/ 5.修改zoo.cfg文件 6.进入/usr/local/zookeeper-3.4.12/zkdat…

虚拟机与主机(win10之间的通信)

(201条消息) Ubuntu虚拟机不显示ip地址【已解决】_ubuntu没有ip_不爱赖床的懒虫的博客-CSDN博客 sudo /sbin/dhclient VMTool安装与卸载 (201条消息) ubuntu中vmtools的安装与彻底卸载_卸载vmtools_林麦安的博客-CSDN博客 (202条消息) 解决虚拟机安装 VMware Tools 灰色无法…

聊聊RocketMQ中的broker的TPS和QPS为何相差巨大,是如何统计的

这里是weihubeats,觉得文章不错可以关注公众号小奏技术&#xff0c;文章首发。拒绝营销号&#xff0c;拒绝标题党 最近在看RocketMQ的一些监控指标的时候&#xff0c;总觉得一些监控指标不太对&#xff0c;好像对不上。 所以打算研究下看看RocketMQ中的 broker TPS、broker QP…

嵌入式学习笔记(60)内存管理之堆

1.7.1.什么是堆&#xff08;heap&#xff09; 内存管理对OS来说是一件非常复杂的事&#xff0c;因为首先内存容量大&#xff0c;其次内存需求在时间和大小块上没有规律&#xff08;OS上运行着几十、几百、几千个进程随时都会申请或者释放内存&#xff0c;申请或者释放的内存块…

JavaWeb从入门到起飞笔记——导学课程

学完这一节&#xff0c;我不知道学Web开发究竟能干什么&#xff1f;你知道吗&#xff1f; 以下是黑马程序员Java从入门到起飞的笔记 一、学完Javaweb能干什么&#xff1f; 学完Java后我们可以独立开发一些后台管理系统&#xff0c;例如CRMER器&#xff0c;京东和淘宝&#x…

tuxera ntfs2024破解版mac电脑磁盘读写软件

大家都知道由于操作系统的原因&#xff0c;在苹果电脑上不能够读写NTFS磁盘&#xff0c;但是&#xff0c;今天小编带来的这款tuxera ntfs 2024 mac版&#xff0c;完美的解决了这个问题。这是一款在macOS平台上使用的磁盘读写软件&#xff0c;能够实现苹果Mac OS X系统读写Micro…

C++ 字符串编码转换封装函数,UTF-8编码与本地编码互转

简介 字符串编码转换封装函数&#xff0c;UTF-8编码与本地编码互转。 中文乱码的解决方法 有时候我们会遇到乱码的字符串&#xff0c;比如&#xff1a; 古文码 可能是用GBK方式读取UTF-8编码的中文导致的&#xff0c;用下面的Utf8ToLocal(string str)函数转换一下就可以了。…

RFID解决光伏难题

RFID解决光伏难题 RFID是无线射频识别&#xff08;Radio Frequency Identification&#xff09;的缩写&#xff0c;是一种通过无线电信号识别物体的技术。RFID系统由标签、读写器和主机系统组成。标签内置有微型芯片和天线&#xff0c;能够储存和传输数据。读写器通过射频信号…

EasyCVR视频智能分析系统如何助力广场流动摊贩监管手段升级

在很多公园广场地带&#xff0c;经常会有流动摊贩进行售卖&#xff0c;虽然国家大力支持“地摊经济”&#xff0c;但很多摊贩并未按照规定进行摆摊&#xff0c;甚至有一些摊贩为了位置、客源大打出手&#xff0c;大大增添了城市管理难度。为让广场摊贩更加规范地进行作业&#…

mybatisplus开启sql打印的三种方式

1、在application.yml文件中添加mybatisplus的配置文件 使用mybatisplus自带的log-impl配置&#xff0c;可以在控制台打印出sql语句、执行结果的数据集、数据结果条数等详细信息&#xff0c;这种方法适合再调试的时候使用&#xff0c;因为这个展示的信息详细&#xff0c;更便于…

Windows11系统安装WSL教程

WSL&#xff0c;全称Windows Subsystem for Linux&#xff0c;是微软官方提供的可以在Windows上直接运行的Linux环境&#xff0c;包括大多数命令行工具、程序和应用&#xff0c;由系统底层虚拟机平台支持。 开启相关服务 1、控制面板-启用或关闭Windows功能 2、勾选以下两个…

Dataspell快捷键更改为eclipse后,在.py文件中shift+回车自动换行冲突问题解决

1.问题描述 已经将Dataspell快捷键切换快捷键为eclipse&#xff0c;在.py文件中shiftenter没有自动换行&#xff0c;出现如下结果。 2.问题解决 进去keymap配置界面 搜索python 将如下快捷键删除。 测试后问题已经解决。

Yakit工具篇:中间人攻击(平替Burp)的相关技巧-01

简介(来自官方文档) 背景 “MITM” 是 “Man-in-the-Middle” 的缩写&#xff0c;意思是中间人攻击。 MITM攻击是一种网络攻击技术&#xff0c;攻击者通过欺骗的手段&#xff0c;让自己成为通信双方之间的中间人&#xff0c;从而可以窃取双方之间的通信内容、修改通信内容、…

ntfs读写工具Tuxera NTFS2023激活码

Tuxera NTFS for Mac是一款mac系统读写工具,Tuxera让Mac OS支持NTFS 格式文件读写,支持所有移动硬盘、U盘等外接设备,同时Tuxera用户可以简单直观的在Mac机上随意对NTFS文件修改、 在 Mac 上打开、编辑、复制、移动或删除存储在 Windows NTFS 格式 USB 驱动器上的文件。当您获…

关于硬件原理图

很多纯软工程师开始做嵌入式时觉得门槛很高&#xff0c;基本的硬件原理图也看不懂&#xff0c;没有学过电路、数电、模电、电路原理&#xff0c;对电子元器件&#xff0c;对电阻、电压、电流、电容、电感等没有很扎实的概念&#xff0c;觉得老虎吃天无从下嘴。打开硬件原理图&a…

在Qt中怎么操作MySQL数据库

一、安装驱动 &#xff08;1&#xff09;安装 在Qt中操作MySQL数据库首先要安装mysql的驱动文件&#xff0c;将MySQL下的libmusql.dll文件复制到Qt的安装路径下的bin文件夹下即可。 本文福利&#xff0c;莬费领取Qt开发学习资料包、技术视频&#xff0c;内容包括&#xff08;…

使用Chrome浏览器进行网页截图

在需要截图的网页上&#xff0c;按F12打开开发调试页面&#xff0c;再按下ShiftCtrlP&#xff0c;打开命令输入框&#xff0c;输入Capture&#xff0c; 此时会弹出4中截图模式&#xff0c;我个人比较喜欢用Capture full size screenshot Capture area screenshot&#xff0c;…