附:红色,部分为重点部分;蓝颜色为需要记忆的部分(不是死记硬背哈,多敲);黑色加粗或者其余颜色为次重点;黑色为描述需要
目录
链表
知识点:
细节:
链表的属性:
1.单链表
单链表的基本框架:
1.1.单链表的结构
单链表的是由数据、指针组成:
typedef struct SListNode
{
SLDateType data;//SLDateType typedef定义类型和顺序表一样都是为了更加方便去改变结构中的存的类型
struct SListNode* next;//定义一个结构体类型的指针,因为到时候next指向一个结构体类型
}SListNode;//用typedef将struct SListNode改变成SListNode这样更方便于我们后面使用(可以不用加上struct,直接用代替的就好)
//typedef int SLDateType; int重命名为SLDateType
1.2放入数据到单链表中
在插入数据之前需要先开辟好空间(也就是创建节点):
SListNode* BuySListNode(SLDateType x) {//接收传进来的数据
SListNode* newnode = (SListNode*)malloc(sizeof(SListNode));//用malloc开辟一个结构体大小的空间给新节点
if (newnode == NULL)//熟系的判断是否申请成功
{
perror("malloc failed");
return NULL;
}
newnode->data = x;//在申请的结构体空间中放入数据
newnode->next = NULL;//将其下一个位置暂时指向NULL
return newnode;//返回这个节点,返回类型是个指针类型也就是newnode的地址
}
申请好空间后就可以进行插入数据(并且链接了)
从指定位置插入数据:
1.3 删除单链表中的数据
在pos位置/pos位置后删除数据
1.4 摧毁单链表
1.5单链表的打印
附:为什么要用二级指针?
因为如果不用二级指针的话就无法改变传进来的参数(只是传调用无法改变参数),所以只有用传址调用能改变形参,而传递进来的是一个一级指针类型,所以我们就需要二级指针类型来接收他的地址(接收指针类型的指针三步法)。
2.带头双向循环列表
知识点:
细节:
带头双向循环链表的基本框架:
2.1带头双向链表的结构
它的结构是由存数据的变量、两个分别指向前后的指针组成的
typedef int LTDataType;
typedef struct ListNode
{
LTDataType data;//数据
struct ListNode* next;//指向后面的数据
struct ListNode* prev;//指向前面的数据
//struct ListNode结构体类型,这里要加上struct因为类型重命名是在后面的
}ListNode;//typedef类型重命名
2.2双向链表的初始化
在那之前还需要去写一个申请空间的接口
ListNode* BuyMemory(LTDataType x)//申请空间的函数
{
ListNode* node = (ListNode*)malloc(sizeof(ListNode));//malloc申请一个大小为一个结构体(一个节点的)空间
if (node== NULL)//若申请失败
{
perror("malloc::BuyMemory");//报错
//return NULL;
exit(-1);//直接退出程序
}
node->data = x;//将申请中的空间数据置为给定的x
node->next = NULL;//将next先置为NULL
node->prev = NULL;//将prev先置为NULL
return node;//返回借号的空间
}
因为是带头的链表所以需要去先申请一个空间给头
ListNode* ListCreate()//给头申请空间并且返回头指针的地址
{
ListNode* head = BuyMemory(-1);//申请空间并且将其数据置为-1
head->next = head;//将next指向head
head->prev = head;//prev也是指向头的
return head;//返回头申请好的空间
}
此处因为有了头,那就不再需要先去创建一个链表的结构(ListNode *STL = NULL )来确定链表的头了(不用传STL/&STL、而是直接传head即可找到链表并且修改链表(即使是改变链表的开始也不用再使用二级指针了))。
下面的头插、头删中的头并不是头而是表示插入/删除第一个节点
2.3双向链表中放入数据
2.4双向链表中的删除数据
在我们删除数据的前提是得链表中有数据所以就需要一个判断是否有数据的接口:
bool If_DTLEmpty(ListNode* pHead)//返回bool值,即返回真或假
{
if (pHead->next == pHead)//就判断phead的->是不是自己即可,因为如果不是则表示是有数据的,反之因为是循环链表没数据就会指向自己了
{
return true;//若指向自己则是真 空的
}
else
{
return false;//反之则非空
}
}
2.5双向链表的摧毁
2.6打印双向链表中的各个数据
3.如何快速的实现一个链表
如果有任何问题欢迎讨论哈!
如果觉得这篇文章对你有所帮助的话点点赞吧!
持续更新大量数据结构细致内容,早关注不迷路。