c语言数据结构单链表中随机链表的复制

c语言数据结构单链表中随机链表的复制

1.随机链表的复制问题

给你一个长度为 n n n的链表,每个节点包含一个额外增加的随机指针 r a n d o m random random ,该指针可以指向链表中的任何节点或空节点。

构造这个链表的 深拷贝。 深拷贝应该正好由 n n n 个 全新 节点组成,其中每个新节点的值都设为其对应的原节点的值。新节点的 n e x t next next 指针和 r a n d o m random random 指针也都应指向复制链表中的新节点,并使原链表和复制链表中的这些指针能够表示相同的链表状态。复制链表中的指针都不应指向原链表中的节点 。

例如,如果原链表中有 X X X Y Y Y 两个节点,其中 X . r a n d o m − − > Y X.random --> Y X.random>Y 。那么在复制链表中对应的两个节点 x x x y y y ,同样有 x . r a n d o m − − > y x.random --> y x.random>y

返回复制链表的头节点。

用一个由 n n n 个节点组成的链表来表示输入/输出中的链表。每个节点用一个 [ v a l , r a n d o m i n d e x ] [val, random_index] [val,randomindex] 表示:
v a l : val: val一个表示 N o d e . v a l Node.val Node.val 的整数。
r a n d o m i n d e x : random_index: randomindex随机指针指向的节点索引(范围从 0 0 0 n − 1 n-1 n1);如果不指向任何节点,则为 n u l l null null
你的代码 只 接受原链表的头节点 h e a d head head 作为传入参数。
示例 1:
在这里插入图片描述

输入: h e a d = [ [ 7 , n u l l ] , [ 13 , 0 ] , [ 11 , 4 ] , [ 10 , 2 ] , [ 1 , 0 ] ] head = [[7,null],[13,0],[11,4],[10,2],[1,0]] head=[[7,null],[13,0],[11,4],[10,2],[1,0]]
输出: [ [ 7 , n u l l ] , [ 13 , 0 ] , [ 11 , 4 ] , [ 10 , 2 ] , [ 1 , 0 ] ] [[7,null],[13,0],[11,4],[10,2],[1,0]] [[7,null],[13,0],[11,4],[10,2],[1,0]]

示例 2:
在这里插入图片描述

输入: h e a d = [ [ 1 , 1 ] , [ 2 , 1 ] ] head = [[1,1],[2,1]] head=[[1,1],[2,1]]
输出: [ [ 1 , 1 ] , [ 2 , 1 ] ] [[1,1],[2,1]] [[1,1],[2,1]]

示例 3:

在这里插入图片描述
输入: h e a d = [ [ 3 , n u l l ] , [ 3 , 0 ] , [ 3 , n u l l ] ] head = [[3,null],[3,0],[3,null]] head=[[3,null],[3,0],[3,null]]
输出: [ [ 3 , n u l l ] , [ 3 , 0 ] , [ 3 , n u l l ] ] [[3,null],[3,0],[3,null]] [[3,null],[3,0],[3,null]]

提示:

  • 0 < = n < = 1000 0 <= n <= 1000 0<=n<=1000
  • − 104 < = N o d e . v a l < = 104 -104 <= Node.val <= 104 104<=Node.val<=104
  • N o d e . r a n d o m Node.random Node.random n u l l null null 或指向链表中的节点

2.解决思路

2.1 复制节点,插入到原节点和下一个节点之间。
在这里插入图片描述
   我们通过遍历,在原节点和下一个节点之间插入复制节点。(在这里我把 c u r cur cur看作被复制的节点, c o p y copy copy看作复制后的节点)
   这样做的好处是: c o p y copy copy r a n d o m random random就很好表示,他就是 c u r . r a n d o m . n e x t cur.random.next cur.random.next
2.2 根据原节点 r a n d o m random random,处理复制节点的 r a n d o m random random
在这里插入图片描述
  由于 c o p y copy copy r a n d o m random random很好表示,我们就可以通过遍历,一一的把 c o p y copy copy r a n d o m random random节点连起来。
2.3 把复制节点解下来链接成一个新链表,恢复原链表链接关系。
在这里插入图片描述
  通过以上的步骤我们就可以通过把复制节点解下来链接成一个新链表,恢复原链表链接关系。以此来完成复制随机链表的目标。

3.代码的实现

// 随机链表的拷贝
struct Node {
	int val;
	struct Node* next;
	struct Node* random;
	
};

struct Node* copyRandomList(struct Node* head) {
	struct Node* cur = head;
	while (cur)
	{
		struct Node* copy = (struct Node*)malloc(sizeof(struct Node));
		copy->val = cur->val;
		// 插入·copy节点
		copy->next = cur->next;
		cur->next = copy;
		cur = copy->next;
	}
	//  根据原节点,处理copy节点的random
	cur = head;
	while (cur)
	{
		struct Node* copy = cur->next;
		if (cur->random == NULL)
		{
			copy->random = NULL;
		}
		else
		{
			copy->random = cur->random->next;
		}
		cur = copy->next;
	}
	// 恢复链表
	struct Node* copyHead = NULL; 
	struct Node* copyTail = NULL;
	cur = head;
	while (cur)
	{
		struct Node* copy = cur->next;
		struct Node* next = copy->next;
		if (copyTail == NULL)
		{
			copyTail = copyHead = copy;
		}
		else
		{
			copyTail->next = copy;
			copyTail = copy;
		}
		cur->next = next;
		cur = next;
	}
	return copyHead;
}

   通过以上代码我们就可以实现用c语言复制随机链表了。


最后,这是我在学习c语言数据结构单链表中随机链表复制时的笔记,我觉得想出这个方法的人真的很厉害,我作为一个初学者现在能做到就是站在巨人的肩膀上,不断提高自己。有不对的地方希望大家能够指出,大家一起加油!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值