【数据结构】带头双向链表,真正的六边形战士

news2024/10/2 16:29:42

文章目录

    • 概要
    • 整体架构流程
    • 小结

概要

*数据结构中的链表在实际开发中应用非常广泛,但写一个链表并不是一件简单的事情。

链表有八种结构,对于刚入门的新手来说,往往会先经历单链表的折磨。
而今天我要讲的带头双向链表非常适合新手学习,它实现起来不像单链表那么繁琐,应用起来更加得心应手,最主要的是它能让我们更好的理解链表。*

整体架构流程

1.创建哨兵位
哨兵位介绍:带头链表俗称哨兵位,哨兵位的作用非常强大,它可以让我们进行头删头插时不使用双指针,增加代码可读性。往往哨兵位里的内容是没有实际意义的,因此也不算做有效节点。

**.h头文件代码**
// 带头+双向+循环链表增删查改实现
typedef int LTDataType;
typedef struct ListNode
{
	LTDataType data;
	struct ListNode* prev;
	struct ListNode* next;
}ListNode;
// 创建返回链表的头结点.(创建哨兵位)
ListNode* ListCreate();

**.c逻辑代码**
// 创建返回链表的头结点.(创建哨兵位)
ListNode* BuyHead(LTDataType x)
{
	ListNode* phead = (ListNode*)malloc(sizeof(ListNode));
	if (phead == NULL)
	{
		perror("malloc fial:");
	}
	phead->data = x;
	phead->next = NULL;
	phead->prev = NULL;
	return phead;
}
ListNode* ListCreate()
{
	ListNode* guard =  BuyHead(-1);
	guard->next = guard;
	guard->prev = guard;
	return guard;
}

2.双向链表销毁

**.h头文件**
// 双向链表销毁
void ListDestory(ListNode* pHead);

**.c逻辑代码**
// 双向链表销毁
void ListDestory(ListNode* pHead)
{
	assert(pHead);
	ListNode* cur = pHead->next;
	while (cur != pHead)
	{
		ListNode* next = cur->next;
		free(cur);
		cur = next;
	}
	free(pHead);
}

3.双向链表打印

**.h头文件**
// 双向链表打印
void ListPrint(ListNode* pHead);

**.c逻辑代码**
// 双向链表打印
void ListPrint(ListNode* pHead)
{
	assert(pHead);
	ListNode* cur = pHead->next;
	printf("Guard<=>");
	while (cur != pHead)
	{
		printf("%d<=>", cur->data);
		cur = cur->next;
	}
	printf("\n");
}

4.双向链表尾插

**.h头文件**
// 双向链表尾插
void ListPushBack(ListNode* pHead, LTDataType x);

**.c逻辑代码**
// 双向链表尾插
void ListPushBack(ListNode* pHead, LTDataType x)
{
	assert(pHead);
	ListNode* tail = pHead->prev;
	ListNode* Tailnext = BuyHead(x);
	tail->next = Tailnext;
	Tailnext->prev = tail;
	Tailnext->next = pHead;
	pHead->prev = Tailnext;
}

在这里插入图片描述

**5.双向链表尾删 **

.h头文件
// 双向链表尾删
void ListPopBack(ListNode* pHead);

.c逻辑代码
//用于判断链表中是否有节点
bool ListEmpty(ListNode* phead)
{
	assert(phead);
	return phead->next == phead;
}
// 双向链表尾删
void ListPopBack(ListNode* pHead)
{
	assert(pHead);
	assert(!ListEmpty(pHead));
	ListNode* tail = pHead->prev;
	ListNode* tailPrev = tail->prev;
	free(tail);
	tailPrev->next = pHead;
	pHead->prev = tailPrev;
}

在这里插入图片描述

6.判断链表中是否有节点

.h文件
//用于判断链表中是否有节点
bool ListEmpty(ListNode* phead);

.c逻辑代码
//用于判断链表中是否有节点
bool ListEmpty(ListNode* phead)
{
	assert(phead);
	return phead->next == phead;
}

7.双向链表头插

.h文件
// 双向链表头插
void ListPushFront(ListNode* pHead, LTDataType x);

.c逻辑代码
// 双向链表头插
void ListPushFront(ListNode* pHead, LTDataType x)
{
	assert(pHead);
	ListNode* newhead = BuyHead(x);
	ListNode* cur = pHead->next;
	pHead->next = newhead;
	newhead->prev = pHead;
	newhead->next = cur;
	cur->prev = newhead;
}

在这里插入图片描述

8.双向链表头删

.h文件
// 双向链表头删
void ListPopFront(ListNode* pHead);

.c逻辑代码
// 双向链表头删
void ListPopFront(ListNode* pHead)
{
	assert(pHead);
	assert(!ListEmpty(pHead));
	ListNode* cur = pHead->next;
	ListNode* headnext = cur->next;
	pHead->next = headnext;
	headnext->prev = pHead;
	free(cur);
}

在这里插入图片描述

9.双向链表查找

.h文件
// 双向链表查找
ListNode* ListFind(ListNode* pHead, LTDataType x);

// 双向链表查找
ListNode* ListFind(ListNode* pHead, LTDataType x)
{
	assert(pHead);
	ListNode* cur = pHead->next;
	while (cur != pHead)
	{
		if (cur->data == x)
		{
			return cur;
		}
		cur = cur->next;
	}
	return NULL;
}

10.双向链表在pos的前面进行插入

.h文件
// 双向链表在pos的前面进行插入
void ListInsert(ListNode* pos, LTDataType x);

.c逻辑代码
// 双向链表在pos的前面进行插入
void ListInsert(ListNode* pos, LTDataType x)
{
	assert(pos);
	ListNode* prev = pos->prev;
	ListNode* newnode = BuyHead(x);
	prev->next = newnode;
	newnode->prev = prev;
	newnode->next = pos;
	pos->prev = newnode;
}

.c测试代码
	//常和查找一起使用
	ListNode* Find = ListFind(p,3);
	if (Find)
	{
		ListInsert(Find, 6);
	}

在这里插入图片描述

11.双向链表删除pos位置的节点

.h头文件
// 双向链表删除pos位置的节点
void ListErase(ListNode* pos);

.c逻辑代码
// 双向链表删除pos位置的节点
void ListErase(ListNode* pos)
{
	assert(pos);
	assert(!ListEmpty(pos));
	ListNode* prev = pos->prev;
	ListNode* next = pos->next;
	prev->next = next;
	next->prev = prev;
	free(pos);
}

.c测试代码
	ListNode* Find = ListFind(p,3);
	if (Find)
	{
		LisErase(Find);
	}

在这里插入图片描述

12.插入(头插、尾插)复用
分析序号10代码,我们可以得到该代码也适用于头插、尾插,因此我们可以将头插、尾插简化:

// 双向链表头插
void ListPushFront(ListNode* pHead, LTDataType x)
{
	assert(pHead);
	ListNode* cur = pHead->next;
	ListInsert(cur, x);
}

// 双向链表尾插
void ListPushBack(ListNode* pHead, LTDataType x)
{
	assert(pHead);
	ListNode* tail = pHead;
	ListInsert(tail, x);
}

13.删除(头删、尾删)复用
分析序号11代码,我们可以得到该代码也适用于头删、尾删,因此我们可以将头删、尾删简化:

// 双向链表头删
void ListPopFront(ListNode* pHead)
{
	assert(pHead);
	ListNode* cur = pHead->next;
	ListErase(cur);
}

// 双向链表尾删
void ListPopBack(ListNode* pHead)
{
	assert(pHead);
	ListNode* tail = pHead->prev;
	ListErase(tail);
}

小结

带头双向链表的实现并不复杂,但需要我们对单链表有一定的了解程度,因此在学习带头双向链表前,最好先学习单链表,带头双向链表虽然被称为六边形战士,但我们也需要先学好基本知识,
再利用好带头双向链表,完全有可能做到十分钟实现链表,谢谢大家!

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

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

相关文章

C++6.类和对象(下)

1.友元函数&#xff0c;一般现在类的最上面。 2.函数的参数中&#xff0c;如果不改变&#xff0c;尽量加上const修饰。 3.对于自定义类型&#xff0c;使用运算符进行操作基本上都要用运算符重载&#xff0c;但是有些运算符重载会默认自动生成。 4.初始化列表&#xff0c;是成…

【wpf】列表类,用相对源时,如何绑定到子项

前言 在之前的一篇文章 &#xff1a;《【wpf】深度解析&#xff0c;Binding是如何寻找数据源的》https://blog.csdn.net/songhuangong123/article/details/126195727#:~:text%E3%80%90wpf%E3%80%91%E6%B7%B1%E5%BA%A6%E8%A7%A3%E6%9E%90%EF%BC%8CBinding%E6%98%AF%E5%A6%82%E4…

读书|林曦:她把自己的生活,过成了无用但丰盈的美学

时代在以加速度的方式变化&#xff0c;让人难以从容。而当我们陷于横向的比较系统&#xff0c;权衡着卷、躺、润时&#xff0c;也有人在探寻另一条纵向的路——向古人学习&#xff0c;以传统美学关照和滋养当下生活。      立夏之际&#xff0c;水墨画家林曦的新作《无用之…

33岁跳槽无路,濒临绝望之际受贵人指点,成功上岸阿里(测试岗)

写在前面 马上过34岁生日了&#xff0c;和大家聊聊最近的情况&#xff0c;半年前还在迷茫该学什么&#xff0c;怎样才能走出现在的困境&#xff0c;半年后已经成功上岸阿里&#xff0c;感谢在这期间帮助我的每一个人 开始 30多岁工作的时候总是有种力不从心的感觉&#xff0…

网络安全工程师需要考什么证吗?

目前网络安全行业&#xff0c;国内都有哪些证书可以考。 一、CISP-PTE &#xff08;国家注册渗透测试工程师&#xff09; CISP-PTE即注册信息安全渗透测试工程师&#xff0c;该证书由中国信息安全测评中心颁发&#xff0c;证书是国内唯一认可的渗透测试认证&#xff0c;专业性…

AIOps社区低代码项目火热报名中|中科院开源之夏2023,万元现金等你来拿!

活动介绍 开源之夏是由中科院软件所“开源软件供应链点亮计划”发起并长期支持的一项暑期开源活动&#xff0c;旨在鼓励在校学生积极参与开源软件的开发维护&#xff0c;培养和发掘更多优秀的开发者&#xff0c;促进优秀开源软件社区的蓬勃发展&#xff0c;助力开源软件供应链…

告别Excel,免费大数据分析与可视化工具,让你的论文图表“高大上”

数据分析工具很多&#xff0c;可以分为表格、数据库、BI工具、编程等四大工具。每个大类又有很多的工具&#xff0c;例如表格包括Excel、WPS、Google Sheets、Airtable等。编程工具包括Python和R。 搞科研几年了&#xff0c;笔者一直都是在使用Excel做数据分析和可视化&#xf…

Go语言中sync.Map、sync.Pool和Context的用法

目录 【sync.Map】 实现线程安全的 map 类型 使用 sync.Map 实现并发读写的map 【sync.Pool】 使用 带缓冲channel 实现对象池 使用 sync.Pool 创建临时对象池 【Context 上下文】 Context应用&#xff1a;实现带超时功能的远程调用 Context应用&#xff1a;监控指令…

电脑找不到MSVCR120.dll怎么办/MSVCR120.dll是什么?

电脑提示找不到MSVCR120.dll怎么办&#xff1f;你是否也遇到这个问题&#xff0c;MSVCR120.dll是什么文件呢&#xff1f;小编今天就把MSVCR120.dll文件丢失的修复方法给大家。msvcr120.dll是Microsoft Visual C 的一部分&#xff0c;它是Windows操作系统中的一个动态链接库文件…

计算卸载-论文05-双层优化(无线充电与卸载)

标题&#xff1a;《A Divide-and-Conquer Bilevel Optimization Algorithm for Jointly Pricing Computing Resources and Energy in Wireless Powered MEC》 期刊&#xff1a;IEEE TRANSACTIONS ON CYBERNETICS&#xff0c;2022 一、理论梳理 问题&#xff1a;相比于移动云…

基于Python长时间序列遥感数据处理及在全球变化、物候提取、植被变绿与固碳分析、生物量估算与趋势分析等领域中的应用

植被是陆地生态系统中最重要的组分之一&#xff0c;也是对气候变化最敏感的组分&#xff0c;其在全球变化过程中起着重要作用&#xff0c;能够指示自然环境中的大气、水、土壤等成分的变化&#xff0c;其年际和季节性变化可以作为地球气候变化的重要指标。此外&#xff0c;由于…

基于MAX-10 FPGA 读取超声波模块HC_SR04距离数据到数码管上

目录 实验现象简单介绍超声波测距模块HC_SR04模块框图模块编写测距信号源距离计算数码管模块顶层模块 总结 实验现象 将MAX-10小脚丫FPGA和超声波模块HC_SR04插在面包板上&#xff0c;用杜邦线将对应的引脚连接好&#xff0c;烧录程序&#xff0c;小脚丫自带的数码管显示距离数…

全网火爆,性能测试面试常问+测试小技巧总结,要卷就卷成最强的...

目录&#xff1a;导读 前言一、Python编程入门到精通二、接口自动化项目实战三、Web自动化项目实战四、App自动化项目实战五、一线大厂简历六、测试开发DevOps体系七、常用自动化测试工具八、JMeter性能测试九、总结&#xff08;尾部小惊喜&#xff09; 前言 性能测试面试常问…

itop-3568开发板驱动学习笔记(26)设备树(五)中断实例分析

《【北京迅为】itop-3568开发板驱动开发指南.pdf》 学习笔记 文章目录 中断控制器配置中断其他属性 中断控制器 设备树中的中断控制器节点和 GPIO 控制器类似&#xff0c;都是由芯片厂家编写&#xff0c;如果是外部中断&#xff0c;中断控制器和 GPIO 控制器是共存的&#xff…

TDengine “亮相” ODSC East,开发者争相驻足交流

最近 TDengine 终于将时序数据技术创新这把火 烧到了美国波士顿 并获得了一众国外开发者的热捧 而这一次 TDengine 的成功落地 还得从两天前的一场数据大会说起... 波士顿当地时间 5 月 9 日&#xff0c;一场名为 ODSC East 的数据技术盛会在波士顿缓缓拉开序幕&#xff0…

YOLO V1-V3 简单介绍

目录 1. YOLO 2. YOLO V1 3. YOLO V2 4. YOLO V3 5. YOLO V3 SPP网络 5.1 Mosaic 图像增强 5.2 SPP 模块 5.3 CIou Loss 5.4 Focal loss 1. YOLO YOLO 是目标检测任务强大的算法&#xff0c;将目标检测的问题转换边界框和相关概率的回归问题&#xff0c;是目标检测…

【JAVA应届生如何提高职场竞争力】从蓝海走向红海的IT世界,新人如何掌握IT技能和找到合适的工作

从蓝海走向红海的IT世界,新人如何掌握IT技能和找到合适的工作。 在当前就业形势下,如何提高应届生在职场中的竞争力?具有哪些有效的方法和策略可供选择?这是一个备受关注的热点话题。哪些方面会对应届生的职场发展起到关键的推动和支撑作用呢? 前段时间有位CSDN的…

更高效便捷的开发体验——Cloud Studio 编辑器命令行工具

Cloud Studio 是一个云端在线开发平台&#xff0c;在 Cloud Studio 的控制台页面中&#xff0c;可以方便快捷创建或者打开一个工作空间。工作空间提供了在线编辑器给大家访问远端开发环境。大部分开发时间都与这个在线编辑器打交道&#xff0c;在线编辑器效果如下图所示&#x…

【刷题之路】LeetCode232——用栈实现队列

一、题目描述 原题链接&#xff1a;https://leetcode.cn/problems/implement-queue-using-stacks/ 题目描述&#xff1a; 请你仅使用两个栈实现先入先出队列。队列应当支持一般队列支持的所有操作&#xff08;push、pop、peek、empty&#xff09;&#xff1a; 实现 MyQueue 类…

深拷贝/浅拷贝精讲

&#x1f353; 简介&#xff1a;java系列技术分享(&#x1f449;持续更新中…&#x1f525;) &#x1f353; 初衷:一起学习、一起进步、坚持不懈 &#x1f353; 如果文章内容有误与您的想法不一致,欢迎大家在评论区指正&#x1f64f; &#x1f353; 希望这篇文章对你有所帮助,欢…