初阶数据结构(C语言实现)——3.3单向非循环链表详解(定义、增、删、查、改)+链表面试题

目录

学习链表之前,建议先学习下顺序表,这是博主的顺序表文章,欢迎学习初阶数据结构(C语言实现)——3顺序表

前置思考

为什么有了顺序表,还要有链表?

  • 顺序表存在一些问题
  1. 中间/头部的插入删除,时间复杂度为O(N)
  2. 增容需要申请新空间,拷贝数据,释放旧空间。会有不小的消耗。
  3. 增容一般是呈2倍的增长,势必会有一定的空间浪费。例如当前容量为100,满了以后增容到200,我们
    再继续插入了5个数据,后面没有数据插入了,那么就浪费了95个数据空间。
  • 为了更好的解决上面的问题,我们引入了链表

3.链表

3.1 链表的概念及结构

概念:链表是一种物理存储结构上非连续、非顺序的存储结构,数据元素的逻辑顺序是通过链表中的指针链接次序实现的

链表的物理结构
在这里插入图片描述

1.从上图可看出,链式结构在逻辑上是连续的,但是在物理上不一定连续

链表的逻辑结构(为了方便理解,想象出来的)
在这里插入图片描述

注意:

  1. 现实中的结点一般都是从堆上申请出来的
  2. 从堆上申请的空间,是按照一定的策略来分配的,两次申请的空间可能连续,也可能不连续

3.2 链表的分类

实际中链表的结构非常多样,以下情况组合起来就有8种链表结构:

  1. 单向或者双向

在这里插入图片描述

  1. 带头或者不带头(哨兵位的头结点,不存储有效数据)

在这里插入图片描述

  1. 循环或者非循环

在这里插入图片描述

链表总共有8种
在这里插入图片描述

虽然有这么多的链表的结构,但是我们实际中最常用还是两种结构:

在这里插入图片描述

  1. 无头单向非循环链表:结构简单,一般不会单独用来存数据。实际中更多是作为其他数据结构的子结构,如哈希桶、图的邻接表等等。另外这种结构在笔试面试中出现很多。
  2. 带头双向循环链表:结构最复杂,一般用在单独存储数据。实际中使用的链表数据结构,都是带头双向循环链表。另外这个结构虽然结构复杂,但是使用代码实现以后会发现结构会带来很多优势,实现反而简单了。

3.3 无头+单向+非循环链表增删查改接口实现

3.3.0 单链表的实现

在这里插入图片描述

typedef int SLTDateType;
//定义单链表节点
typedef struct SListNode
{
   
	SLTDateType data; //数据域
	struct SListNode* next;//指针域
}SListNode;//重命名为SListNode,方便我们后面定义结构体变量。就不需要每次写 struct SListNode 这么一长串了
  • 实现接口

// 动态申请一个节点
SListNode* BuySListNode(SLTDateType x);
// 单链表打印
void SListPrint(SListNode* phead);
// 单链表尾插
void SListPushBack(SListNode** pphead, SLTDateType x);
// 单链表的头插
void SListPushFront(SListNode** pphead, SLTDateType x);
// 单链表的尾删
void SListPopBack(SListNode** pphead);
// 单链表头删
void SListPopFront(SListNode** pphead);
// 单链表查找
SListNode* SListFind(SListNode* phead, SLTDateType x);
// 单链表在pos位置之后插入x
void SListInsertAfter(SListNode* pos, SLTDateType x);
// 单链表删除pos位置之后的值
void SListEraseAfter(SListNode* pos);

3.3.1 动态申请节点和释放销毁节点

动态申请一个结点

// 动态申请一个节点
SListNode* BuySListNode(SLTDateType x)
{
   
	SListNode* newnode = (SListNode*)malloc(sizeof(SListNode));
	if (newnode == NULL)//申请完,检查是否开辟成功
	{
   
		perror("BuySListNode::mallo fail!");
		return NULL;
	}
	newnode->data = x;
	newnode->next = NULL;
	return newnode;
}

释放(销毁)所有节点

//销毁(释放)所有节点
void SLListDistory(SListNode** pphead
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值