链队列的实现_队列的链式结构为什么要另写一个linkqueue 而不写到linknode中-程序员宅基地

链队列存储结构
在这里插入图片描述
链队列的结点为结构体QNode;队列结构体LinkQueue,用来管理链队列,包含两个结点指针front和rear。

typedef int ElemType;	//队列元素类型
typedef struct QNode {
    	//结点
	ElemType data;
	QNode* next;
}QNode,*QueuePtr;

struct LinkQueue {
    
	QueuePtr front;		//队头指针
	QueuePtr rear;		//队尾指针
};

在这里插入图片描述

注意:
链队列包含一个头结点,是为了方便队列的操作,头结点没有有效数据,在队列初始化时就分配的头结点;
队头始终指向头结点,头结点指向首结点;队尾指向最后一个结点。当队列为空时,front和rear都指向头结点。
尾结点后为空,可以以NULL作为结束条件,遍历到后面包括尾结点的所有结点。
在这里插入图片描述
基本操作

1.初始化
分配一个头结点,将队列的front和rear指针指向头结点,头结点下一个结点为NULL。

void InitQueue(LinkQueue& Q) {
    
	Q.front = Q.rear = (QueuePtr)malloc(sizeof(QNode));
	if (!Q.front)	exit(-1);
	Q.front->next=NULL;
}

2.销毁
在这里插入图片描述
销毁后包括头结点在内的链表都被释放,只有队列结构体LinkQueue,将里面的数据清空。
队尾元素后为空,所以以为空作为结束的条件。

void DestroyQueue(LinkQueue& Q) {
    
	while (Q.front) {
    
		Q.rear = Q.front->next;
		free(Q.front);
		Q.front = Q.rear;
	}
}
void DestroyQueue(LinkQueue& Q) {
    
	QueuePtr p;
	while (Q.front != Q.rear) {
    
		p = Q.front->next;
		free(Q.front);
		Q.front= p;
	}
	free(Q.rear);
	Q.front = Q.rear = NULL;
}

3.清空
在这里插入图片描述
队列清空时,还有头结点,队列的front和rear指针都指向头结点。

void ClearQueue(LinkQueue& Q) {
    
	QueuePtr p = Q.front->next,q;//p指向首结点
	Q.rear=Q.front;
	Q.front->next = NULL;
	while (p) {
    
		q = p->next;
		free(p);
		p = q;
	}
}
void ClearQueue(Queue &Q) {
    
	QueuePtr p=Q.front->next,q;	//p指向首结点
	while (p) {
    
		q = p->next;
		free(p);
		p = q;
	}
	Q.rear = Q.front;
	Q.rear->next = NULL;
}

4.队空
队首后不为空时或者队首等于队尾时为空

bool QueueEmpty(LinkQueue Q) {
    
	if (Q.front->next==NULL)
		return true;
	else
		return false;
}
bool QueueEmpty(Queue Q) {
    
	if (Q.rear == Q.front)
		return true;
	else
		return false;
}

5.长度
由队首遍历到队尾并计数。

int QueueLength(LinkQueue Q) {
    
	int n = 0;
	QueuePtr p = Q.front;
	while (p != Q.rear) {
    
		p=p->next;
		++n;
	}
	return n;
}

6.队头
队列不为空时,返回队头元素。队头为front指针的下一个位置。

bool GetHead(LinkQueue Q,ElemType &e) {
    
	if (Q.front==Q.rear)	//队空
		return false;
	e = Q.front->next->data;
	return true;
}

7.入队
在队尾Q.rear后插入元素,注意最后要改变尾指针指向。

void EnQueue(LinkQueue& Q, ElemType e) {
    
	QueuePtr p = (QueuePtr)malloc(sizeof(QNode));
	if (!p)		exit(-1);// 存储分配失败
	p->data = e;
	p->next = NULL;
	Q.rear->next = p;
	Q.rear=p;	//改变尾指针指向
}

8.出队
队列不为空时,释放头结点后的节点;注意,如果只有一个结点时,出队后队列为空,需要将队尾指针指向头结点。

bool DeQueue(LinkQueue& Q, ElemType& e) {
    
	if (Q.front == Q.rear)	return false;	//队空
	QueuePtr p = Q.front->next;	//p指向首结点
	e = p->data;
	Q.front->next = p->next;
	if (Q.rear == p)//队列只有一个元素要改变尾指针指向
		Q.rear = Q.front;
	free(p);
	return true;
}

9.遍历
从队首遍历到队尾。

void QueueTraverse(LinkQueue Q,void(*vi)(ElemType)) {
    
	QueuePtr p = Q.front->next;	//p指向首结点
	while (p) {
    
		vi(p->data);
		p = p->next;
	}
	printf("\n");
}

测试函数

#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>

void visit(ElemType e)
{
    
	printf("%d ", e);
}

int main() {
    
	ElemType n;
	LinkQueue q;
	InitQueue(q);
	printf("成功地构造了一个空队列!\n");
	printf("是否空队列?%d(1:空 0:否) ", QueueEmpty(q));
	printf("队列的长度为%d\n", QueueLength(q));
	EnQueue(q, -5);
	EnQueue(q, 5);
	EnQueue(q, 10);
	printf("插入3个元素(-5,5,10)后,队列的长度为%d\n", QueueLength(q));
	printf("是否空队列?%d(1:空 0:否) ", QueueEmpty(q));
	printf("队列的元素依次为");
	QueueTraverse(q, visit);
	if (GetHead(q, n))
		printf("队头元素是:%d\n", n);
	DeQueue(q, n);
	printf("删除了队头元素%d\n", n);
	if (GetHead(q, n))
		printf("新的队头元素是:%d\n", n);
	ClearQueue(q);
	printf("清空队列后,q.front=%u q.rear=%u q.front->next=%u\n", q.front, q.rear, q.front->next);
	DestroyQueue(q);
	printf("销毁队列后,q.front=%u q.rear=%u\n", q.front, q.rear);
}

测试结果
在这里插入图片描述

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/qq_43604517/article/details/103214784

智能推荐

《机器学习》西瓜书课后习题3.5——python实现线性判别分析_西瓜书3.5-程序员宅基地

文章浏览阅读5.2k次,点赞7次,收藏74次。《机器学习》西瓜书课后习题3.5——python实现线性判别分析《机器学习》西瓜书P693.5 编程实现线性判别分析,并给出西瓜数据集3.0a上的结果理论学习参见文章:线性判别分析LDA原理总结注意:在该文章中针对w的求法出现了两种方式,一种是w=S−1w(μ0−μ1)w=S^-1 w(μ_0−μ_1)w=S−1w(μ0​−μ1​)该方法指的应该是针对二类LDA,所以我们在解决西瓜数据集问题是求w的方法采用此方法。另一种方法是:计算S−1wSb的最大的d个特征值和对应的d个特征向量(_西瓜书3.5

Android最全面的HTTP基础知识_android http-程序员宅基地

文章浏览阅读2.2k次。一、计算机网络体系结构目前,由国际化标准组织ISO制定的网络体系结构国际标准是 OSI七层模型。OSI的七层协议体系结构的概念清楚,理论也比较完整,但它既复杂又不实用。TCP/IP体系结构则不同,但它却得到了非常广泛的应用。TCP/IP是一个四层的体系结构,它包含应用层、运输层、网际层和网络接口层(用网际层这个名字是强调这一层是为了解决不同网络的互联问题)。不过从实质上讲,TCP/IP只有最..._android http

代码解释似然函数_rand_pick-程序员宅基地

文章浏览阅读246次。#encoding: utf-8'''案例 弹出硬币10次 参数 a(0< a <1)代表硬币正面朝上的概率,反面朝上的概率为 1-a。求参数a的值首先思考在已知最后结果的前提下,表达当前概率函数的表达式 [a]^y1*[1-a]^(1-yi)= Y, yi对应标签Y代表当前的硬币的结果的概率,似然函数就是上述表达式累成的结果。我们重复试验10次 。'''import..._rand_pick

为传递函数自动设定PID参数——pidtune学习笔记-程序员宅基地

文章浏览阅读1.4w次,点赞6次,收藏55次。装置模型和PID控制器的基本模型在命令行里设计PID控制器装置模型为一个传递函数:sys=1(s+1)3s y s=\frac{1}{(s+1)^{3}}sys=(s+1)31​首先创建一个装置的模型sys,并设计一个简单的PI控制器sys = zpk([],[-1 -1 -1],1);% C_pi是一个PI开环控制器[C_pi,info] = pidtune(sys,'Pi'..._pidtune

Python + OpenCV : 已知多边形轮廓的点坐标,自动识别多边形顶点坐标的算法_python排序多边形轮廓坐标点-程序员宅基地

文章浏览阅读8k次,点赞8次,收藏66次。Python + OpenCV : 已知多边形轮廓的点坐标,自动识别多边形顶点坐标的算法最近做工程,根据提供的目标物体的坐标(比如说分割结果输出的目标像素坐标),标其中遇到了RT说述问题,OpenCV并没有提供现成的函数,并且网上关于这块几乎没有内容,所以在这里记录一下。先来啰嗦一下两个基础函数,熟悉可略过。基础函数1.OpenCV提供了cv2.drawContours()函数可根据所提供的边界点绘制任何形状的轮廓。eg:cv2.drawContours(image, [np.array(point_python排序多边形轮廓坐标点

egret_渲染优化-spine粒子混合_spine粒子特效-程序员宅基地

文章浏览阅读1.7k次。之前的 spine 动画, 优化是的图集, 这里主要是 spine 中的粒子 缘起: 在项目中发现了某个 spine 粒子特效 特别费 dc, 看了下 spine相关文件, 法线只是使用一个小图, 预期中应该是 一个批次就可以绘制完成. 遂 详细看了下 spine 的 json 文件. 发现使用了一个混合 &quot;blend&quot;: &quot;additive&quot;粒子主要是很多个 渲染节..._spine粒子特效

随便推点

Permission denied (publickey,gssapi-keyex,gssapi-with-mic) 解决方法-程序员宅基地

文章浏览阅读1.2k次。今天在使用服务直接互连的时候出现Permission denied (publickey,gssapi-keyex,gssapi-with-mic) 。经过网上查找,现在主要做个笔记解决方法就是在修改一个配置/etc/ssh/sshd_config在里面增加如下内容sudo vim /etc/ssh/sshd_config增加如下修改PasswordAuthentication yessudo systemctl restart sshd然后我使用的是root,又增加如下内容/etc/_permission denied (publickey,gssapi-keyex,gssapi-with-mic)

Final %Shell高级版 激活,只需3步_finalshell高级版-程序员宅基地

文章浏览阅读1.8w次,点赞32次,收藏62次。1.点击输入2.复制机器码3.执行程序程序源码:package test;import java.io.IOException;import java.security.MessageDigest;import java.security.NoSuchAlgorithmException;import java.util.Scanner;public class FinalShell { public static void main(String[] args) throw_finalshell高级版

DDPG算法详解-程序员宅基地

文章浏览阅读1.9k次,点赞2次,收藏14次。在RL领域,DDPG主要从:PG -> DPG -> DDPG 发展而来。_ddpg算法详解

如何在Anaconda中安装Opencv和pillow_conda install pillow-程序员宅基地

文章浏览阅读2.3k次,点赞3次,收藏8次。Anaconda中库的安装基本可以分为以下三步:以管理员身份打开Anaconda Prompt,在该命令框中按顺序进行以下三步:建立一个虚拟环境激活环境,并安装库测试安装。下面以Opencv安装为例(也可以直接安装,无需建立虚拟环境)一、Opencv安装建立一个虚拟环境(我的python是3.6,可根据自己版本选择)conda create --name opencv-env python=3.6回车之后,结果如下:2. 激活环境,并安装cv2有的可以在代码前加入sourc_conda install pillow

Vue通过for循环随机生成不同的颜色或随机数_let r = math.floor(math.random() * 256); let g = m-程序员宅基地

文章浏览阅读1.4w次,点赞3次,收藏6次。需求:随机生成不同的如下图标的背景颜色方法:本来通过计算属性渲染出随机颜色,然而计算属性是一次性获取值,即使你把RandomColor引入v-for中也没有用,得到的只会永远是同一颜色,除非刷新页面颜色才改变,但是还是没法实现五颜六色的功能,因此,换了中思路,直接在v-for循环中加入随机生成颜色代码,即可快速得到不同颜色的方块。 computed: { RandomColo..._let r = math.floor(math.random() * 256); let g = math.floor(math.random() *

Java -verbose:gc命令_verbose:gc +printgcdetails-程序员宅基地

文章浏览阅读421次。Java -verbose:gc 中参数-verbose:gc 表示输出虚拟机中GC的详细情况.使用后输出如下:[Full GC 168K->97K(1984K), 0.0253873 secs]解读如下:  箭头前后的数据168K和97K分别表示垃圾收集GC前后所有存活对象使用的内存容量,说明有168K-97K=71K的对象容量被回收,括号内的数据1984_verbose:gc +printgcdetails

推荐文章

热门文章

相关标签