队列(数据结构)——C语言

目录

1.概念与结构

2.队列的实现

初始化QueueInit

申请新节点BuyNode

入队QueuePush

判断队为空QueueEmpty

出队QueuePop

读取队头数据QueueFront

读取队尾数据QueueBack

元素个数QueueSize

销毁队列QueueDestroy

3.整体代码

(文章中结点和节点是同一个意思)

1.概念与结构

概念:只允许在⼀端进⾏插⼊数据操作,在另⼀端进⾏删除数据操作的特殊线性表,队列具有先进先 出FIFO(First In First Out)

⼊队列:进⾏插⼊操作的⼀端称为队尾

出队列:进⾏删除操作的⼀端称为队头

队列也可以数组和链表的结构实现,使⽤链表的结构实现更优⼀些,因为如果使⽤数组的结构,出列在数组头上出数据,需要将后面所有的元素整体向前移动一位,时间复杂度为o(n),效率会⽐较低,入队操作是单链表需要遍历整个链表找到尾结点,所以这里定义一个头结点和尾结点,来避免入队操作时间复杂度高。

2.队列的实现

创建三个文件,Queue.h,Queue.c,test.c,分别为头文件,函数实现文件,以及测试文件

Queue.h

#pragma once
#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#include<stdbool.h>typedef int DataType;typedef struct QueueNode
{DataType data;struct QueueNode* next;
}QueueNode;typedef struct Queue
{QueueNode* phead;QueueNode* ptail;int size;
}Queue;void QueueInit(Queue*pq);
// 销毁队列
void QueueDestroy(Queue * pq);//入队列--队尾
void QueuePush(Queue* pq, DataType x);
//出队列--队头
void QueuePop(Queue* pq);//取队头数据
DataType QueueFront(Queue* pq);
//取队尾数据
DataType QueueBack(Queue* pq);//队列判空
bool QueueEmpty(Queue* pq);
//队列有效元素个数
int QueueSize(Queue* pq);

这里很之前的一样,栈里存的元素。可以是各种数据类型,为了方便后续改成其他类型,这里重定义数据类型为SDataType,这里以int为例,定义结构体队列的节点,这里利用结构体的自引用,用来找到下一个结点,即next;以及队列的头结点,和尾结点,队列的元素个数;还有实现各种函数的申明。

初始化QueueInit

void QueueInit(Queue* pq)
{assert(pq);pq->phead = pq->ptail = NULL;pq->size = 0;
}

断言传的指针非空,头结点和尾结点置为空,元素个数为零。

申请新节点BuyNode

QueueNode* BuyNode(DataType x)
{QueueNode* newnode = (QueueNode*)malloc(sizeof(QueueNode));if (newnode == NULL){perror("malloc fail!");exit(1);}newnode->data = x;newnode->next = NULL;return newnode;
}

这里返回类型为结构体QueueNode*类型,利用malloc函数申请,申请成功后,再将结构体的data赋值为x,下一个结点,即next置为空。

入队QueuePush

void QueuePush(Queue* pq, DataType x)
{assert(pq);QueueNode*newnode= BuyNode(x);if (pq->phead ==NULL){pq->phead = pq->ptail = newnode;}else{pq->ptail->next = newnode;pq->ptail = pq->ptail->next;}pq->size++;
}

断言传的指针非空,申请一个节点,判断队是否为空,如果为空直接将新的结点,赋给头结点和尾结点,如果不为空,则在尾结点后面插入,(很前面单链表尾插一样,只是这里已经有尾结点了,不需要遍历单链表),最后元素个数++;

判断队为空QueueEmpty

bool QueueEmpty(Queue* pq)
{assert(pq);return pq->phead==NULL;
}

这里返回类型为bool型,断言传的指针非空,通过判断头结点是否为NULL,为空则队列中没有元素。

出队QueuePop

void QueuePop(Queue* pq)
{assert(pq);assert(!QueueEmpty(pq));if (pq->phead == pq->ptail){free(pq->phead);pq->phead = pq->ptail = NULL;}else{QueueNode* next = pq->phead->next;free(pq->phead);pq->phead = next;	}pq->size--;	
}

断言传的指针非空,以及判断队列非空,出队要考虑两种情况,如果队列中只有一个节点,即头结点和尾结点指向同一个,直接释放掉头结点,然后头结点和尾结点置为空就行了,如果不止一个节点,则删除头结点指向那个结点,头结点指向下一个结点,(和单链表的头插一模一样),最后元素个数——。

读取队头数据QueueFront

DataType QueueFront(Queue* pq)
{assert(pq);assert(!QueueEmpty(pq));return pq->phead->data;
}

断言传的指针非空,以及判断队列非空,直接返回头结点的data。

读取队尾数据QueueBack

DataType QueueBack(Queue* pq)
{assert(pq);assert(!QueueEmpty(pq));return pq->ptail->data;
}

断言传的指针非空,以及判断队列非空,直接返回尾结点的data。

元素个数QueueSize

int QueueSize(Queue* pq)
{assert(pq);return pq->size;
}

断言传的指针非空,直接返回结构体Queue中的size,即为队列元素个数。

销毁队列QueueDestroy

void QueueDestroy(Queue* pq)
{assert(pq);QueueNode* pcur = pq->phead;while (pcur){QueueNode* next = pcur->next;free(pcur);pcur = next;}pq->phead = pq->ptail = NULL;pq->size = 0;
}

断言传的指针非空,定义一个指针指向头结点,遍历链表,依次删除(这里和前面的单链表销毁的函数也是一模一样),最后将头结点,和尾结点都置为空,元素个数置为0.

3.整体代码

Queue.h

#pragma once
#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#include<stdbool.h>typedef int DataType;typedef struct QueueNode
{DataType data;struct QueueNode* next;
}QueueNode;typedef struct Queue
{QueueNode* phead;QueueNode* ptail;int size;
}Queue;void QueueInit(Queue*pq);
// 销毁队列
void QueueDestroy(Queue * pq);//入队列--队尾
void QueuePush(Queue* pq, DataType x);
//出队列--队头
void QueuePop(Queue* pq);//取队头数据
DataType QueueFront(Queue* pq);
//取队尾数据
DataType QueueBack(Queue* pq);//队列判空
bool QueueEmpty(Queue* pq);
//队列有效元素个数
int QueueSize(Queue* pq);

Queue.c

#include"Queue.h"
void QueueInit(Queue* pq)
{assert(pq);pq->phead = pq->ptail = NULL;pq->size = 0;
}QueueNode* BuyNode(DataType x)
{QueueNode* newnode = (QueueNode*)malloc(sizeof(QueueNode));if (newnode == NULL){perror("malloc fail!");exit(1);}newnode->data = x;newnode->next = NULL;return newnode;
}
void QueuePush(Queue* pq, DataType x)
{assert(pq);QueueNode*newnode= BuyNode(x);if (pq->phead ==NULL){pq->phead = pq->ptail = newnode;}else{pq->ptail->next = newnode;pq->ptail = pq->ptail->next;}pq->size++;
}void QueuePop(Queue* pq)
{assert(pq);assert(!QueueEmpty(pq));if (pq->phead == pq->ptail){free(pq->phead);pq->phead = pq->ptail = NULL;}else{QueueNode* next = pq->phead->next;free(pq->phead);pq->phead = next;	}pq->size--;	
}DataType QueueFront(Queue* pq)
{assert(pq);assert(!QueueEmpty(pq));return pq->phead->data;
}DataType QueueBack(Queue* pq)
{assert(pq);assert(!QueueEmpty(pq));return pq->ptail->data;
}bool QueueEmpty(Queue* pq)
{assert(pq);return pq->phead==NULL;
}int QueueSize(Queue* pq)
{return pq->size;
}void QueueDestroy(Queue* pq)
{assert(pq);QueueNode* pcur = pq->phead;while (pcur){QueueNode* next = pcur->next;free(pcur);pcur = next;}pq->phead = pq->ptail = NULL;pq->size = 0;
}

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

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

相关文章

keil兼容C51和ARM,C251

三合一 C51,AEM,C251获取STC32的包 将 C51,AEM,C251安装到一块。 C51,AEM,C251 将三个软件分别下载到不同的文件夹KEIL,MDK,KEIL2里。 然后打开KEIL,MDK,KEIL2文件夹&#xff0c;复制KEIL文件夹里的C51和KEIL2文件夹里的C251的文件夹到MDK文件夹里。 打开KEIL和KEIL2文件夹里…

单链表的经典算法OJ

目录 1.反转链表 2.链表的中间节点 3.移除链表元素 ——————————————————————————————————————————— 正文开始 1.反转链表 typedef struct ListNode ListNode; struct ListNode* reverseList(struct ListNode* head) {//判空if(…

运行kafka查看所有主题Topic报错zookeeper is not a recognized option

执行命令查看&#xff1a;./kafka-topics.sh --list --zookeeper localhost:2181 报错 zookeeper is not a recognized option joptsimple.UnrecognizedOptionException: zookeeper is not a recognized optionat joptsimple.OptionException.unrecognizedOption(OptionExcept…

000010 - Mapreduce框架原理

Mapreduce框架原理 1. InputFormat 数据输入1.1 切片与 MapTask 并行度决定机制1.2 Job 提交流程源码和切片源码详解1.2.1 Job 提交流程源码详解1.2.2 FileInputFormat 切片源码解析&#xff08;input.getSplits(job)&#xff09; 1.3 FileInputFormat 切片机制1.3.1 切片机制1…

二、PyCharm基本设置

PyCharm基本设置 前言一、设置中文汉化二、设置代码字体颜色三、设置鼠标滚轮调整字体大小四、修改 PyCharm 运行内存4.1 方式一4.1 方式二 五、显示 PyCharm 运行时内存六、设置代码模版配置的参数有&#xff1a; 七、PyCharm设置背景图总结 前言 为了让我们的 PyCharm 更好用…

一家射频芯片企业终止,报告期持续亏损,高端产品占比不足

飞骧科技终止原因如下&#xff1a;飞骧科技从事的射频芯片行业如今竞争激烈&#xff0c;飞骧科技的产品主要应用于中低端手机&#xff0c;如摩托罗拉、传音&#xff0c;相比同行业上市公司已经退出的低集成度市场&#xff0c;相关产品展飞骧科技业务比重仍然不低。交易所质疑其…

【Matlab】基于Prandtl−Ishlinskii的迟滞模型-RLS辨识

PI模型 PI迟滞模型的输出公式&#xff1a; 代码记录 此代码为根据PI模型&#xff0c;已知输入&#xff08;正弦函数幅值为3.5&#xff09;、阈值以及权重值&#xff0c;利用matlab生成迟滞回线。 %% The Prandtl-Ishlinskii Hysteresis Model- %% 20241021 clc;clear; close…

数据结构与算法——Java实现 44.翻转二叉树

目录 226. 翻转二叉树 思路 代码 本地代码测试 不管前方的路有多苦 只要走的方向正确 不管多么崎岖不平 都比站在原地更接近幸福 —— 24.10.21 226. 翻转二叉树 给你一棵二叉树的根节点 root &#xff0c;翻转这棵二叉树&#xff0c;并返回其根节点。 示例 1&#xff1a; 输…

Unity AnimationClip详解(2)——动画数据的优化

【内存优化】 首先要意识到运行时和编辑时的区别&#xff0c;当运行时和编辑时所需的数据相差不大时&#xff0c;我们用同一套数据结构即可&#xff0c;当两者差异较多或者数据量很大时&#xff0c;需要有各自的数据结构&#xff0c;这意味着在打包或构建时需要将编辑时数据转…

【Linux探索学习】第七弹——Linux的工具(二):Linux下vim编辑器的使用详解

Linux的工具&#xff08;一&#xff09;&#xff1a;【Linux探索学习】第六弹——Linux的工具&#xff08;一&#xff09;&#xff1a;Ubuntu系统下的软件包管理器_ubuntu软件管理器-CSDN博客 前言&#xff1a; 在学习Linux之前&#xff0c;相信大家都或多或少的学习过一些计算…

微信小程序用开发工具在本地真机调试可以正常访问摄像头,发布了授权后却无法访问摄像头,解决方案

今天开发上线了一个拍照的微信小程序&#xff0c;用uniapp的Vue3开发的&#xff0c;调用的camera组件&#xff0c;相关代码如下&#xff1a; <!-- 微信小程序相机组件 --><view v-if"showCamera" class"camera-container"><camera :device…

Adobe Acrobat DC 打印PDF文件,没有打印出注释的解决方法

adobe acrobat在打印的时候&#xff0c;打印不出来注释内容&#xff08;之前一直可以&#xff0c;突然就不行&#xff09;&#xff0c;升级版本、嵌入字体等等都试过&#xff0c;也在Google找了半天和问了GPT也么找着办法。 无奈之下&#xff0c;自己通过印前检查&#xff0c;…

免费开源AI助手,颠覆你的数字生活体验

Apt Full作为一款开源且完全免费的软件&#xff0c;除了强大的自然语言处理能力&#xff0c;Apt Full还能够对图像和视频进行一系列复杂的AI增强处理&#xff0c;只需简单几步即可实现专业级的效果。 在图像处理方面&#xff0c;Apt Full提供了一套全面的AI工具&#xff0c;包…

Windows环境下Qt Creator调试模式下qDebug输出中文乱码问题

尝试修改系统的区域设置的方法&#xff1a; 可以修复问题。但会出现其它问题&#xff1a; 比如某些软件打不开&#xff0c;或者一些软件界面的中文显示乱码&#xff01; 暂时没有找到其它更好的办法。

《YOLO目标检测》—— YOLO的简单介绍及Map评估指标

文章目录 一、简单概述二、YOLO中的Map指标1.定义与计算2.应用与意义3.注意事项 一、简单概述 YOLO&#xff08;You Only Look Once&#xff09;是一种目标检测算法&#xff0c;由Redmon等人在2016年提出。它的主要特点是速度快且准确性高&#xff0c;非常适合用于实时目标检测…

C# WebApi 接口测试工具:WebApiTestClient应用技术详解

目录 一、引言 二、WebApiTestClient介绍 1、特性 2、应用场景 三、WebApiTestClient具体使用 1、WebApi项目引入组件 2、如何使用组件 1、修改Api.cshtml文件 2、配置读取注释的xml路径 3、测试接口 四、总结 一、引言 由于最近项目需要开发WebApi接口&…

热更新解决方案2 —— Lua语法相关知识点

概述 开发环境搭建 Lua语法 1.第一个Lua程序 2.变量 print("******变量*******"); --lua当中的简单变量类型 -- nil number string boolean -- lua 中所有的变量声明 都不需要声明变量类型 它会自动的判断类型 -- 类似C# 中的var --lua中的一个变量 可以随便赋值 ——…

Java开发中知识点整理

正则表达式 测试网址 Git 分支和主分支有冲突 先checkout origin/分支把origin/master pull进本地分支 修改冲突MergeCommit and Push

旧电脑安装Win11提示“这台电脑当前不满足windows11系统要求”,安装中断。怎么办?

前言 最近有很多小伙伴也获取了LTSC版本的Win11镜像&#xff0c;很大一部分小伙伴安装这个系统也是比较顺利的。 有顺利安装完成的&#xff0c;肯定也有安装不顺利的。这都是很正常的事情&#xff0c;毕竟这个镜像对电脑硬件要求还是挺高的。 有一部分小伙伴在安装Windows11 …

用Python删除PDF文档页面的页边距

在处理PDF文档时&#xff0c;有时候我们会遇到PDF文件带有较大的页边距的情况。这样过大的页边距不仅浪费了页面空间&#xff0c;而且在打印或电子阅读时也可能影响用户体验。通过删除这些不必要的页边距&#xff0c;我们可以更有效地利用页面区域&#xff0c;使得内容更加紧凑…