【数据结构】顺序表和单链表!开山神作!

🎁个人主页:泡泡大虾-优快云博客

​ 🔍系列专栏:数据结构_泡泡大虾的博客-优快云博客

​ 🌟渴望·得到真正的救赎,而不是暂时的pain killer

​ 🌱欢迎大家点赞👍评论📝收藏⭐文章


引言

(一)链表的创建以及初始化

1.结点的创建


2.结点中数据的初始化

  • 首先创建一个个的结点
  • 然后是对其结点里面初始化以及明确指向关系



(二)链表的打印 | SLTPrint

1.传值 || 传参??

  • 思考这个是传值or传参运算?
  • 为啥是传递的SLTNode* phead 而不是传递SLTNode** pphead作为打印函数的参数呢?

  • 以及为什么不直接 使用SLTNode plist 来作为函数的参数呢?

2.代码展示

//链表的打印
void SLTPrint(SLTNode* phead)
{
	SLTNode* pcur = phead;
	while ()
	{
		printf("%d -> ", pcur->data); //打印结点数据
		pcur = pcur->next;
	}
	printf("NULL\n");  //打印结束后注意换行
}


(三)尾插/头插

1.尾部插入数据

原理说明

两种情况需要考虑

尾插操作的两种场景

尾插操作的本质是找到链表最后一个节点,然后将其 next 指针指向新节点。但需要区分两种情况:

  • 场景1:链表为空(head == null),此时新节点直接成为头节点。
  • 场景2:链表非空,需要遍历到最后一个节点再插入。 

如果跳过空指针判断,直接尝试遍历链表,会导致对 null 解引用(如 pcur->next),从而引发程序崩溃。

代码演示

//尾部插入
void SLTPushBack(SLTNode** pphead, SLTDataType x);
//头部插入
void SLTPushFront(SLTNode** pphead, SLTDataType x);
//头尾部的删除
void SLTPopBack(SLTNode** pphead, SLTDataType x);
void SLTPopFront(SLTNode** pphead, SLTDataType x);

2.头部插入数据

自己思考!延展思维!


(四)尾删/头删

1.尾部删除数据

原理说明

明白坑点:自己写的时候,只单单定义了两个变量phead和ptail,然而在面对了尾部结点后,变量太少了,没办法写出来删除和另个指向的操作来!

也可以自己定义几个其他变量来,虽然有点指针名称不规范罢了 

 尾删的两种情况(关键区别)

场景链表长度核心操作注意事项
单节点删除1直接释放头节点并置空*pphead必须置空头指针,防止悬垂指针
多节点删除≥2找到倒数第二个节点并断开尾节点双指针遍历,避免访问非法内存

 代码演示

//尾删
void SLTPopBack(SLTNode** pphead)
{
	//自己独立写一遍+画图理解后再看视频讲解确实能够更加清晰理解
	assert(pphead && *pphead);

	//只有一个结点
	if ((*pphead)->next == NULL)
	{
		free((*pphead));
		*pphead = NULL;
	}
	else {
		//#1. 定义指针
		SLTNode* ptail = *pphead;
		SLTNode* prev = NULL;
		//#2. 找prev  ptail
		while (ptail->next)
		{
			//走之前,要存prev到ptail结点里面去(画图真香!!)
			prev = ptail;
			ptail = ptail->next;
		}
		prev->next = NULL;
		free(ptail);
		ptail = NULL;

	}

2.头部删除数据

原理图解


代码演示

//头删
void SLTPopFront(SLTNode** pphead)
{
	SLTNode* temp = (*pphead)->next; // 保存下一个节点
	free(*pphead);					 // 释放当前头节点
	*pphead = temp;		             // 更新头指针指向下一个节点
}

(五)查找

// 查找
SLTNode* SLTFind(SLTNode* phead, SLTDataType x);
//在pos之前插⼊数据
void SLTInsert(SLTNode** pphead, SLTNode* pos, SLTDataType x);
//删除pos结点
void SLTErase(SLTNode** pphead, SLTNode* pos);
//在pos之后插⼊数据
void SLTInsertAfter(SLTNode* pos, SLTDataType x);
//删除pos之后的结点
void SLTEraseAfter(SLTNode* pos);
//销毁链表
void SListDestroy(SLTNode** pphead);

(六)在指定位置插入、删除数据

1.在pos之前插入数据

原理图解


代码演示


2.在pos之后插入数据

原理图解


代码演示


3.删除pos结点

原理图解


代码演示


4.删除pos之后的结点

原理图解


代码演示


(七)销毁链表

代码演示


🌲各位同学好,我是  泡泡大侠  !

🌳祝愿各位得到真正的救赎,你值得拥有一个幸福的生活!

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值