双向循环链表

Posted 语风之

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了双向循环链表相关的知识,希望对你有一定的参考价值。

目录

一、链表的概念

1. 链表的概念

2. 链表相邻结点不连续

二、双向循环链表的相关函数

1. 创建链表结点(增)

(1)创建结点

(2)尾插结点

2. 删除链表结点(删)

3. 查找链表结点(查)

4. 修改链表结点(改)

三、归纳总结

四、源码链接


一、链表的概念

1. 链表的概念

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

双向循环链表示意图

2. 链表相邻结点不连续

由图可知,00A99740+12=00A9974C!=00A99788,即物理存储结构上相邻结点不连续

	ListPushBack(Head, 1);//尾插法生成结点
	ListPushBack(Head, 2);
	ListPrint(Head);      //打印链表
	ListFind(Head,1);     //查找结点
	ListFind(Head,2);
	printf("一个结点的内存大小为:%d\\n",sizeof(ListNode));

链表相邻结点地址不连续

二、双向循环链表的相关函数

1. 创建链表结点(增)

(1)创建结点

a. 在堆上申请空间

	ListNode* Node = (ListNode*)malloc(sizeof(ListNode));
	if (NULL == Node)//判断申请空间是否失败
		assert(0);
		return 0;
	

b. 存储数据

	Node->data= data;
	Node->next = NULL;
	Node->pre = NULL;

c. 返回结点地址

	return Node;

(2)尾插结点

假设结点newNode尾插在结点A后面

a. newNode的next指针指向头结点Head

newNode->next=Head ;

b. newNode的prev指针指向结点Head的prev所指向的结点(即A)

newNode->pre=Head->pre ;

c. A的next(即Head->pre->next)指向结点neNode

Head->pre->next = newNode;

d. newHead的prev指向结点P

Head->pre = newNode;
尾插图解

2. 删除链表结点(删)

a. 创建temp指针,指向Head->next所指向的结点

ListNode* temp = (*Head)->next;

b. 通过循环删除temp所指向的结点

	while (temp != *Head)
        //Head的next指向temp
		(*Head)->next = temp->next;
		free(temp);
		temp = (*Head)->next;
	
        //删除temp所指向的结点后,temp再次指向Head->next所指向的结点

c. 删除头结点

	free(*Head);
	*Head = NULL;

3. 查找链表结点(查)

a. 创建指针temp,指向头结点Head的下一个结点

ListNode* temp = Head->next;

b. 使用while循环寻找结点

	while (temp!= Head)
		temp = temp->next;
	

c.创建flag变量判断是否找到结点

若flag==0,则未找到结点;若flag==1,则未找到结点;

		int flag = 0;
        //找到结点
        if (temp->data ==x)
			printf("%d的地址为%p\\n",x,temp);
			flag = 1;
			break;
		
        //未找到结点
        if (0 == flag)
		    printf("%d不在链表中\\n",x);
	    

4. 修改链表结点(改)

a. 找到结点

ListNode* temp=ListFind(Head, x);

b. 修改内容

	LTDataType flag = 0;
	printf("请输入你要修改的数字:");
	scanf("%d",&flag);
	temp->data = flag;

三、归纳总结

带头双向循环链表是链表中结构最复杂的,但使用代码实现以后会发现结构会带来很多优势,实现反而简单了。

(1)链表在物理存储结构上不连续

(2)链表尾插,请注意结点的链接顺序,避免断连。

Head->prev先链接newNode,造成找不到结点A(即无法使用Head->prev找到结点A),出现A的next无法连接newNode的情况。

结点指针断连

四、源码链接

小伙伴们,关于双向循环链表的源码就在这里了,请点击链接。欢迎关注,欢迎问答,我一定会尽力解答你们的疑惑的。
 

以上是关于双向循环链表的主要内容,如果未能解决你的问题,请参考以下文章

(java实现)双向循环链表

数据结构——带头双向循环链表

《链表》之带头双向循环链表

数据结构之单向不循环链表

单链表及其基本操作

数据结构开发(11):双向循环链表的实现