速学数据结构 | 链表实现队列究竟有什么优势?


在这里插入图片描述

🎬 鸽芷咕:个人主页

 🔥 个人专栏:《速学数据结构》 《C语言进阶篇》

⛺️生活的理想,就是为了理想的生活!

📋 前言

  🌈hello! 各位宝子们大家好啊,栈区的实现我们前面已经讲了,而栈和队列都是特殊的线性表,今天我们就来看看队列是怎么实现的!
  ⛳️队列:只允许在一端进行插入数据操作,在另一端进行删除数据操作的特殊线性表,队列具有先进先出FIFO(First In First Out)的特点。
  📚本期文章收录在《数据结构&算法》,大家有兴趣可以看看呐
  ⛺️ 欢迎铁汁们 ✔️ 点赞 👍 收藏 ⭐留言 📝!

文章目录

  • 📋 前言
  • 一、 队列的概念及结构
  • 二、 队列的实现
    • 2.1 队列的结构
    • 2.2 队列的初始化
    • 2.3 队尾入队列
    • 2.4 对头出队列
    • 2.5 获取队列头部元素
    • 2.6 获取队列队尾元素
    • 2.7 获取队列中有效元素个数
    • 2.8 判断队列是否为空
    • 2.9 销毁队列
  • 📝全篇总结

一、 队列的概念及结构

队列:只允许在一端进行插入数据操作,在另一端进行删除数据操作的特殊线性表,队列具有先进先出FIFO(First In First Out),其实理解起来很简单就像我们排队一样先排队的像打到饭然后出队列。

  • 而队列的主要操作就是下面俩条:
  • 入队列:进行插入操作的一端称为队尾
  • 出队列:进行删除操作的一端称为队头

在这里插入图片描述

二、 队列的实现

队列其实也可以用我们学过的数组或者链表实现但是,用数组的话头删要把整个尾部的数据拉过来覆盖前面消耗太大了。所以我们选择使用链表实现出队列头删的时候只要是否头结点到下一个节点就好了。

  • 队列也可以数组和链表的结构实现,使用链表的结构实现更优一些
  • 如果使用数组的结构,出队列在数组头上出数据,效率会比较低

在这里插入图片描述

2.1 队列的结构

那么队列的结构该如何定义呢?首先我们选择用链表来实现队列肯定要先定义一个单链表来进行连接和存放数据:

  • 而队列又需要获取头部和尾部的数据所以:
  • 又需要定义一个头指针和尾指针来指向链表的头和尾。
  • 还要获取队列长度怎么办呢?
  • 就在定义一个 size 来记录队列的长度就可以非常简单的解决问题了

📚 代码演示:

typedef int QDataType;
typedef struct QueueNode
{struct QueueNode* next;QDataType data;
}QNode;typedef struct Queue
{QNode* head;QNode* tail;int size;
}Que;

2.2 队列的初始化

队列的初始化,刚开始的时候队列什么数据都没有所以 headtail 他们指向空就好了。

  • size 目前也没有数据初始化为零可以了
  • 还要注意传进来的是否为空指针

📚 代码演示:

// 初始化队列 
void QueueInit(Que* pq)
{assert(pq);pq->head = pq->tail = NULL;pq->size = 0;
}

2.3 队尾入队列

入队列就很简单了,每次需要了就去 malloc 一个节点然后尾插到 队列后面就好了。

  • 但是也要注意一种情况:
  • 一个是队列为空是的插入

📚 代码演示:

// 队尾入队列 
void QueuePush(Que* pq, QDataType x)
{assert(pq);QNode* newnode = (QNode*)malloc(sizeof(QNode));if (newnode == NULL){perror("malloc fail");exit(-1);}newnode->data = x;newnode->next = NULL;if (pq->tail == NULL){pq->head = pq->tail = newnode;}else{pq->tail->next = newnode;pq->tail = newnode;}pq->size++;
}

2.4 对头出队列

出队列就简单了,先判断一下队列是否为空。为空就直接返回

  • 不为空就直接 free() 掉前一个节点,然后 front 向前走到下一个节点
  • 还要考虑最后一个节点的时候删除怎么办
  • 然后 size-- 数据不要忘记了

📚 代码演示:

void QueuePop(Que* pq)
{assert(pq);assert(!QueueEmpty(pq));if (pq->head->next == NULL){free(pq->head);pq->head = pq->tail = NULL;}else{QNode* next = pq->head->next;free(pq->head);pq->head = next;}pq->size--;
}

2.5 获取队列头部元素

由于我们已经定义了一个头指针,所以直接找到 front 里面存放的元素返回就OK了,是不是非常简单。

📚 代码演示:

// 获取队列头部元素 
QDataType QueueFront(Que* pq)
{assert(pq);assert(!QueueEmpty(pq));return pq->head->data;
}

2.6 获取队列队尾元素

队尾元素可对头是一样的,先判断指针是否为空,和队列是否为空。

📚 代码演示:

// 获取队列队尾元素 
QDataType QueueBack(Que* pq)
{assert(pq);assert(!QueueEmpty(pq));return pq->tail->data;
}

2.7 获取队列中有效元素个数

大家看到这个是不是觉得就是小卡拉米,一下就搞定了:

  • 前面我们定义了一个 size 用来记录队列的元素这个时候就派上用场了。

📚 代码演示:

// 获取队列中有效元素个数 
int QueueSize(Que* pq)
{assert(pq);return pq->size;
}

2.8 判断队列是否为空

大家想一想什么时候队列尾空呢?是不是只有 front == break 的时候才为空啊!

  • 因为只有这样 队列的数据是一个都没存储的

📚 代码演示:

// 检测队列是否为空,如果为空返回非零false,如果非空返回true
bool QueueEmpty(Que* pq)
{assert(pq);return pq->head == NULL;
}

2.9 销毁队列

销毁队列就和以前一样了,先把每个节点都用循环销毁了。在把俩个队列指针置空

  • 数据有效个数szie为0 ,这样就可以销毁队列了

📚 代码演示:

void QueueDestroy(Que* pq)
{assert(pq);QNode* cur = pq->head;while (cur){QNode* next = cur->next;free(cur);cur = next;}pq->head = pq->tail = NULL;pq->size = 0;
}

📝全篇总结

☁️ 好啦以上就是队列实现的全部过程了,相比较链表来说这些更像是链表的扩展只要链表掌握的好这些都是非常简单的!
看到这里了还不给博主扣个:
⛳️ 点赞☀️收藏 ⭐️ 关注

💛 💙 💜 ❤️ 💚💓 💗 💕 💞 💘 💖
拜托拜托这个真的很重要!
你们的点赞就是博主更新最大的动力!
有问题可以评论或者私信呢秒回哦。
在这里插入图片描述

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

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

PointNet 论文阅读

论文链接 PointNet Abstract 对于点云问题,由于其格式不规则,大多数研究人员将此类数据转换为规则的 3D 体素网格或图像集合。然而,这会导致数据不必要地庞大并导致问题在本文中,我们设计了一种直接消耗点云的新型神经网络&…

vue二维码生成插件qrcodejs2-fix、html生成图片插件html2canvas、自定义打印内容插件print-js的使用及问题总结

一、二维码生成插件qrcodejs2-fix 1.安装命令 npm i qrcodejs2-fix --save2.页面使用 import { nextTick } from vue; import QRCode from qrcodejs2-fix; nextTick(() > {let codeView document.querySelector("#codeView");codeView.innerHTML ""…

PDF 表单直接保存到您的文档中--TX Text Control

TX Text Control .NET Server for ASP.NET Document Viewer 32.0.2 允许用户保存包含已填写表单字段的文档,从而更轻松地协作和共享信息。 TX Text Control .NET Server for ASP.NET 是一个适用于 ASP.NET 和 ASP.NET Core 的综合服务器端文档处理库。功能包括 PDF …

C++多态基础

文章目录 1.多态概念2.多态使用3.多态析构4.多态隐藏5.多态原理5.1.单类继承5.1.1.问题一:非指针或引用无法调用多态5.1.2.问题二:同类对象共用虚表5.1.3.问题三:子类对象拷贝父类对象虚表5.1.4.问题四:打印虚表地址和虚表内容 5.…

Java8 Stream API全面解析——高效流式编程的秘诀

文章目录 什么是 Stream Api?快速入门流的操作创建流中间操作filter 过滤map 数据转换flatMap 合并流distinct 去重sorted 排序limit 限流skip 跳过peek 操作 终结操作forEach 遍历forEachOrdered 有序遍历count 统计数量min 最小值max 最大值reduce 聚合collect 收集anyMatch…

CorelDRAW2023最新版本号24.5.0.731

CDR2023是一款近年来备受瞩目的工具软件,它提供了数据存储、分析以及处理的能力。但是,对于许多用户来说,CDR2023到底好用不好用还需要进行深入的分析和探讨。在本文中,我们将从多个角度分析CDR2023这款软件。 CorelDRAW2023版win…

springboot--外部环境配置

外部环境配置 前言1、配置优先级配置文件优先级如下(后面的覆盖前面的)测试 2、外部配置3、导入配置4、属性占位符 前言 场景:线上应用如何快速修改配置,并引用最新配置? springBoot 使用配置优先级外部配置 简化配置…

《网络协议》01. 基本概念

title: 《网络协议》01. 基本概念 date: 2022-08-30 09:50:52 updated: 2023-11-04 07:28:52 categories: 学习记录:网络协议 excerpt: 互联网、网络互连模型(OSI,TCP/IP)、计算机通信基础。 comments: false tags: top_image: /i…

请求地址‘/operlog‘,发生未知异常

👨🏻‍💻 热爱摄影的程序员 👨🏻‍🎨 喜欢编码的设计师 🧕🏻 擅长设计的剪辑师 🧑🏻‍🏫 一位高冷无情的编码爱好者 大家好,我是全栈工…

vue2和vue3区别

Vue2 和 Vue3 双向绑定方法不同 总结 vue3中没有$set Vue2 和 Vue3 双向绑定方法不同 Vue2 : Object.defineProperty() Vue3 : new Proxy()vue3 实例 数据会更新 const addBtn () >{obj.c 3; } vue2实例 问题:数据更新了视图没更新 Object.defineProperty…

Swift语言配合HTTP写的一个爬虫程序

下段代码使用Embassy库编写一个Swift爬虫程序来爬取jshk的内容。我会使用proxy_host为duoip,proxy_port为8000的爬虫IP服务器。 使用Embassy库编写一个Swift爬虫程序可以实现从网页上抓取数据的功能。下面是一个简单的步骤: 1、首先,需要在X…

【踩坑及思考】浏览器存储 cookie 最大值超过 4kb,或 http 头 cookie 超过限制值

背景 本地生产环境:超过最大值 cookie token 不存储;客户生产环境:打开系统空白,且控制台报 http 400 错误; 出现了两种现象 现象一:浏览器对大于 4kb 的 cookie 值不存储 导致用户名密码登录&#xff…

开发知识点-PHP从小白到拍簧片

从小白到拍簧片 位异或运算(^ )引用符号(&)strlen() 函数base64_encode预定义 $_POST 变量session_start($array);操作符php 命令set_time_limit(7200)isset()PHP 命名空间(namespace)new 实例化类extends 继承 一个类使用另一个类方法error_reporti…

FreeRTOS_事件标志组

目录 1. 事件标志组简介 2. 创建事件标志组 2.1 函数 xEventGroupCreate() 2.2 函数 xEventGroupCreateStatic() 3. 设置事件位 3.1 函数 xEventGroupClearBits() 3.2 函数 xEventGroupClearBitsFromISR() 3.3 函数 xEventGroupSetBits() 3.4 函数 xEventGroupSetB…

leetcode:387. 字符串中的第一个唯一字符

一、题目 函数原型 int firstUniqChar(char* s) 二、算法 设置一个大小为26的字符数组,位置0 - 25 分别对应字符 a - z 。遍历两次字符串,第一次记录下每个字符出现的次数,第二次检查哪个字符最先遍历到且出现次数为1,返回该字符即…

uniapp新建的vuecli项目启动报错并且打包失败的问题(已解决)

我的项目新建流程如下 运行之后就是如下报错 解决办法: 安装如下依赖: npm i postcss-loader autoprefixer8.0.0 npm run build 编译失败 安装如下依赖: npm install postcss8.2.2 最终package.json文件如下 {"name": "ls…

【Vue】vant上传封装方法,van-uploader上传接口封装

项目场景&#xff1a; 问题描述 提示&#xff1a;这里描述项目中遇到的问题&#xff1a; 在移动端项目中&#xff0c;使用vant组件上传&#xff0c;但是vant没有上传方法&#xff0c;需要自己写。 html代码 <van-uploader v-model"fileList" :max-size"50…

jvm实践

说一下JVM中的分代回收 堆的区域划分 1.堆被分为了两份:新生代和老年代[1:2] 2.对于新生代&#xff0c;内部又被分为了三个区域。Eden区&#xff0c;幸存者区survivor(分成from和to)[8:1:1] 对象回收分代回收策略 1.新创建的对象&#xff0c;都会先分配到eden区 2.当伊园内存…

谷歌推出基于AI的产品图像生成工具;[微软免费课程:12堂课入门生成式AI

&#x1f989; AI新闻 &#x1f680; 谷歌推出基于AI的产品图像生成工具&#xff0c;帮助商家提升广告创意能力 摘要&#xff1a;谷歌推出了一套基于AI的产品图像生成工具&#xff0c;使商家能够利用该工具免费创建新的产品图像。该工具可以帮助商家进行简单任务&#xff08;…

李宏毅机器学习笔记.Flow-based Generative Model(补)

文章目录 引子生成问题回顾&#xff1a;GeneratorMath BackgroundJacobian MatrixDeterminant 行列式Change of Variable Theorem简单实例一维实例二维实例 网络G的限制基于Flow的网络构架G的训练Coupling LayerCoupling Layer反函数计算Coupling Layer Jacobian矩阵计算Coupli…