【链表-双向链表】

链表-双向链表

  • 1.链表的分类
    • 1.1 分类依据
    • 1.2 常用类型
  • 2.双向链表的
    • 2.1 双向链表的结构
    • 2.2 双向链表的操作
      • 2.2.1 **初始化**
      • 2.2.2 **尾插**
      • 2.2.3 **头插**
      • 2.2.4 **尾删**
      • 2.2.5 **头删**
      • 2.2.6 在pos位置之后插入数据
      • 2.2.7 删除pos节点
      • 2.2.8 查找
      • 2.2.9 销毁

1.链表的分类

1.1 分类依据

单向or双向
在这里插入图片描述
带头or不带头
(一般会称d1为头节点,但实际上head这个哨兵节点才是头节点)
在这里插入图片描述
循环or不循环
在这里插入图片描述
综上所述,222共有8种链表

1.2 常用类型

我们一般最常用的就是单链表和双链表。
单链表:不带头单向不循环链表
在这里插入图片描述

双向链表:带头双向循环链表
在这里插入图片描述

2.双向链表的

2.1 双向链表的结构

双向链表包含三个部分,:
1.数据
2.指向下一个节点的指针
3.指向上一个节点的指针

struct ListNode
{
	int data;
	struct ListNode* next;
	struct ListNode* prev;
}

ps:单链表和双向链表的初始状态?
单链表为空链表
双向链表剩下一个头结点(即哨兵位)

2.2 双向链表的操作

2.2.1 初始化

方法一

void LTInit(LTNode** pphead);
void LTInit(LTNode** pphead)
{
	//给双向链表创建一个哨兵位
	*pphead = LTBuyNode(-1);//哨兵位不存储有效数据
}

方法二

LTNode* LTInit();
LTNode* LTInit()
{
	LTNode* phead = LTBuyNode(-1);
	return phead;
}

打印双向链表
在这里插入图片描述

void LTPrint(LTNode* phead);
void LTPrint(LTNode* phead)
{
	LTNode* pcur = phead->next;
	while (pcur != phead)
	{
		printf("%d->", pcur->data);
		pcur = pcur->next;
	}
	printf("\n");
}

void LTInit(LTNode** pphead)
{
	//给双向链表创建一个哨兵位
	*pphead = LTBuyNode(-1);//哨兵位不存储有效数据
}

2.2.2 尾插

在这里插入图片描述

//尾插
void LTPushBack(LTNode* phead, LTDataType x);
//尾插
void LTPushBack(LTNode* phead, LTDataType x)
{
	assert(phead);//哨兵位空,那就不是一个有效的双向链表
	LTNode* newnode = LTBuyNode(x);

	//phead phead->prev newnode
	newnode->prev = phead->prev;//新节点头指向原链表的尾节点
	newnode->next = phead;//新节点尾节点指向哨兵位

	phead->prev->next = newnode;//原本的尾节点phead->prev指向新的尾节点
	phead->prev = newnode;//哨兵位指向新的尾节点
}

2.2.3 头插

在这里插入图片描述

void LTPushFront(LTNode* phead, LTDataType x); 
void LTPushFront(LTNode* phead, LTDataType x)
{
	assert(phead);
	LTNode* newnode = LTBuyNode(x);

	//phead newnode phead->next
	newnode->next = phead->next;
	newnode->prev = phead;

	phead->next->prev = newnode;
	phead->next = newnode;
}

2.2.4 尾删

在这里插入图片描述

void LTPopBack(LTNode* phead);
void LTPopBack(LTNode* phead)
{
	//链表必须有效且链表不能为空(只有一个哨兵位)
	assert(phead && phead->next != phead);

	LTNode* del = phead->prev;
	//phead del->prev del
	del->prev->next = phead;
	phead->prev = del->prev;

	//删除del节点
	free(del);
	del = NULL;
}

2.2.5 头删

在这里插入图片描述

void LTPopFront(LTNode* phead);
void LTPopFront(LTNode* phead)
{
	assert(phead && phead->next != phead);

	LTNode* del = phead->next;

	//phead del del->next
	phead->next = del->next;
	del->next->prev = phead;

	//删除del节点
	free(del);
	del = NULL;
}

2.2.6 在pos位置之后插入数据

在这里插入图片描述

void LTInsert(LTNode* pos, LTDataType x);
void LTInsert(LTNode* pos, LTDataType x)
{
	assert(pos);

	LTNode* newnode = LTBuyNode(x);
	//pos newnode pos->next
	newnode->next = pos->next;
	newnode->prev = pos;

	pos->next->prev = newnode;
	pos->next = newnode;
}

2.2.7 删除pos节点

在这里插入图片描述

void LTErase(LTNode* pos);
void LTErase(LTNode* pos)
{
	//pos理论上来说不能为phead,但是没有参数phead,无法增加校验
	assert(pos);
	//pos->prev pos pos->next
	pos->next->prev = pos->prev;
	pos->prev->next = pos->next;

	free(pos);
	pos = NULL;
}

PS:LTErase参数理论上要传二级,因为我们需要让形参的改变影响到实参,但是为了保持接口一致性才传的一级。

2.2.8 查找

LTNode* LTFind(LTNode* phead, LTDataType x);
LTNode* LTFind(LTNode* phead, LTDataType x)
{
	LTNode* pcur = phead->next;
	while (pcur != phead)
	{
		if (pcur->data == x)
		{
			return pcur;
		}
		pcur = pcur->next;
	}
	//没有找到
	return NULL;
}

2.2.9 销毁

在这里插入图片描述

void LTDesTroy(LTNode* phead);
void LTDesTroy(LTNode* phead)
{
	assert(phead);

	LTNode* pcur = phead->next;
	while (pcur != phead)
	{
		LTNode* next = pcur->next;
		free(pcur);
		pcur = next;
	}
	//此时pcur指向phead,而phead还没有被销毁
	free(phead);
	phead = NULL;
} 

ps:LTDestroy参数理论上要传二级,因为我们需要让形参的改变影响到实参,但是为了保持接口一致性才传的一级。传一级存在的问题是,当形参phead置为NULL后,实参plist不会被修改为NULL,因此解决办法是:调用完方法后手动将实参置为NULL。

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

翻译技巧早操练-(减译法)

hello,大家好,今天继续来学习翻译的技巧篇第二个-减译法。 往期回顾 翻译早操练-(增译法)-CSDN博客 减译法的目的就是为了译入语表达的通顺,如果原文的一些表达直接翻译到译入语即累赘还不合时宜,那么可以采…

【启明智显技术分享】基于ESP32-S3方案的彩屏固件烧录指南

前言: 【启明智显】专注于HMI(人机交互)及AIoT(人工智能物联网)产品和解决方案的提供商,我们深知彩屏显示方案在现代物联网应用中的重要性。为此,我们一直致力于为客户提供彩屏显示方案相关的技…

主播美颜技术探秘:计算机视觉赋能的直播美颜SDK

今天,我们将深入探讨直播美颜技术背后的计算机视觉原理,以及赋能这一技术的直播美颜SDK。 一、计算机视觉与直播美颜 计算机视觉是一门研究如何使机器“看”的学科,它利用数字图像处理和模式识别等技术,使计算机能够模拟人类视觉…

STL速查

容器 (Containers) 图解容器 支持随机访问 stringarrayvectordeque支持支持支持支持 string 类 构造函数 string(); ------创建一个空的字符串 例如: string str;string(const char* s); ------使用字符串s初始化string(const string& str); ------拷贝构造 赋值操作…

打破次元壁!Stable Diffusion将现实影像转成二次元动画,推特转赞10k+,网友:都可以重做《神奇宝贝》动漫了

破次元壁计划已启动! 就在最近,有网友分享了一个用Stable Diffusion打造二次元动画的工具,直接在网上爆火。 先快来看一波效果。 万物皆可妙化为二次元,耳机也可蜕变成小兔兔: 瞧!连易拉罐的拉环也化身成…

【GPT调用】本地使用python调用GPT接口

python调用GPT接口 环境变量设置主调用方法执行结果 环境变量设置 .env文件中配置GPT环境变量 api_key"你的GPT-API-KEY" urlhttps://ai-proxy.ksord.com/wps.openai.azure.com/openai/deployments/gpt-4-32k/chat/completions?api-version2023-09-01-preview主调…

Oracle SQL Developer导出数据库表结构,表数据,索引以及序列号等对象

通过Oracle SQL Developer软件将指定oralce数据库中的表结构,表数据,索引以及序列号等对象导出成SQL文件。 数据库版本:Oracle Database 11g Express Edition Release 11.2.0.2.0 - 64bit Production 软件版本:Oracle SQL Develo…

【千帆平台】使用AppBuilder零代码创建应用,Excel表格数据转为Markdown格式文本

欢迎来到《小5讲堂》 这是《千帆平台》系列文章,每篇文章将以博主理解的角度展开讲解。 温馨提示:博主能力有限,理解水平有限,若有不对之处望指正! 目录 前言创建应用应用名称应用描述应用头像角色指令组件能力开场白推…

【Python】一道字典题目

题目:输入一段文本,统计每个字符的个数 in_inputinput(“输入:”) dic{} for char in in_input: if char in dic: dic[char]1 # 字典添加键值对的方法,给字典给键和值的方法 else: dic[char]1 print(dic) 输出台:

构建一个快速数据分析(boruta+shap+rcs)的shiny APP

构建一个快速数据分析(borutashaprcs)的shiny APP 之前提出了一个快速数据分析的流程,包括: 变量筛选,使用Boruta等变量筛选的方法来找出相关的变量;发现规律,使用SHAP分析的散点图、交互作用图…

如何使用Python下载哔哩哔哩(Bilibili)视频字幕

在本文中,我将向大家展示如何使用Python下载哔哩哔哩(Bilibili)视频的字幕。通过这个方法,你可以轻松地获取你喜欢的视频的字幕文件,方便学习和交流。 准备工作 在开始之前,我们需要安装一些必要的库&…

第一个C++项目

文章目录 一、新建项目1.打开软件,选择“创建新项目”2.新建项目栏中,按自己的需求来设置项目模板,项目名称和文件存放位置,设置好后点击“确认”3. 点击“Next”4. 按照自己需求设置,设置完后,点击“Next”…

【Linux 性能详解】CPU性能篇

目录 平均负载(Load Average) CPU上下文切换 进程上下文切换 线程上下文切换 中断上下文切换 中断 硬中断 软中断 CPU使用率 性能分析工具 平均负载(Load Average) 平均负载?这个词对很多人来说&#xff0c…

【新三个数排序的自创算法,这是我厉年来很满意的一次排序算法设计,最好小于O(N)最坏O((NN/3)/2)。】2024-5-7

缘由如何用C&#xff0b;&#xff0b;解决一下问题_编程语言-CSDN问答 int a[]{1, 4, 7, 8, 5, 2, 3, 6, 9, 7}, n 10, x n, jh 0, j 0;px:if (j < n) {//缘由https://ask.csdn.net/questions/8099444if (--x < 2 j)x n - 1, j 3;if (x < n - 1 && a[x…

【强训笔记】day14

NO.1 思路&#xff1a;用一个哈希表&#xff0c;先遍历s1&#xff0c;统计哈希表内的字符个数&#xff0c;在遍历s2&#xff0c;s2中的字符在哈希表中减去&#xff0c;如果哈希表中的字符个数小于0那么就输出No。 代码实现&#xff1a; #include <iostream> #include&…

湘潭大学数据库作业题完整答案

作业一&#xff1a; 考虑如下所示的关系数据库。这些关系上适当的主码是什么&#xff1f; 职工&#xff08;姓名&#xff0c;街道&#xff0c;城市&#xff09; 工作&#xff08;姓名&#xff0c;公司名&#xff0c;工资&#xff09; 公司&#xff08;公司名&#xff0c;城市&a…

UVa1376/LA3661 Animal Run

UVa1376/LA3661 Animal Run 题目链接题意输入格式输出格式 分析AC 代码 题目链接 UVA - 1376 Animal Run 题意 由于控制程序出了 bug&#xff0c;动物园的笼子无缘无故被打开&#xff0c;所有动物展开了一次大逃亡。整个城市是一个网格&#xff0c;另外每个单位方格都有一条从…

win平台c语言引入开源库的问题与解决,以引入cJSON库为例

目录 遇到的问题 开源依赖库引入的问题 问题的解决 生成dll文件 方式一 方式二 在VsCode中如何使用开源库 文件放置位置 配置文件进行配置 引入头文件 结束 许久不写博客&#xff0c;五一还在加班&#xff0c;就浅浅写一篇吧。 最近除了做物联网平台,还对网关二次开…

如何恢复手机视频?手机视频恢复软件有哪些?

随着手机使用的普及&#xff0c;我们的日常生活、工作甚至娱乐都与它息息相关。而在其中&#xff0c;我们宝贵的视频文件则是记录下我们生活、工作和重要时刻的重要载体。然而&#xff0c;当这些视频文件不幸丢失或被误删&#xff0c;我们的内心往往会感到一阵恐慌。这时候&…

团队执行力差,多半都是管理的问题

在日常管理中&#xff0c;我们习惯用“执行力好不好”来评价一个团队的表现&#xff0c;但实际上&#xff0c;执行力更应该是一个管理者需要思考和解决的问题&#xff0c;而非单纯归咎于团队。 我们需要明确一点&#xff1a;执行力不是团队的问题&#xff0c;而是管理者的问题…