第35题:LeetCode138. Copy List with Random Pointer

本文介绍了一种复杂链表结构的深度拷贝方法,该链表的节点除包含常规的next指针外,还包含指向链表中任意节点的随机指针。通过在原链表中插入克隆节点并调整指针,实现了高效的空间和时间复杂度。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目 

给定一个链表,每个节点包含一个额外增加的随机指针,该指针可以指向链表中的任何节点或空节点。

要求返回这个链表的深度拷贝。 


考点

1.hash 空间换时间 On^2->On

2.双指针,野指针的鲁棒判断


思路

1.复制节点到原链表后面。

copy->link->next 。只复制节点的值和next,不复制随机指针。cloneNode->random=nullptr;


2.复制对应的随机指针。

重置双指针->如果原节点有随机指针就copy->next


3.分解两个链表。

重新赋值两个指针->ori先走->clone后走->next

 


代码

/*
 * @lc app=leetcode.cn id=138 lang=cpp
 *
 * [138] 复制带随机指针的链表
 *
 * https://leetcode-cn.com/problems/copy-list-with-random-pointer/description/
 *
 * algorithms
 * Medium (23.92%)
 * Total Accepted:    3.6K
 * Total Submissions: 15.1K
 * Testcase Example:  '{}'
 *
 * 给定一个链表,每个节点包含一个额外增加的随机指针,该指针可以指向链表中的任何节点或空节点。
 * 
 * 要求返回这个链表的深度拷贝。 
 * 
 */
/**
 * Definition for singly-linked list with a random pointer.
 * struct RandomListNode {
 *     int label;
 *     RandomListNode *next, *random;
 *     RandomListNode(int x) : label(x), next(NULL), random(NULL) {}
 * };
 */
class Solution {
public:
    RandomListNode *copyRandomList(RandomListNode *head) {
        if(!head )
            return head; 

        //1.clone linked list
        RandomListNode *oriNode  =   head;             
        while(oriNode)
        {
            RandomListNode *cloneNode  =   new RandomListNode(0); 
            //copy
            cloneNode->label   =   oriNode->label;
            cloneNode->next    =   oriNode->next;
            cloneNode->random  =   nullptr; 
            //link
            oriNode->next =   cloneNode; 
            //next
            oriNode       =   cloneNode->next;
        } 
        
        //2.clone random pointer
        oriNode   =   head; 
        while(oriNode)
        {
            //cloneNode
            RandomListNode *cloneNode   =   oriNode->next;
            //copy randomNode
            if(oriNode->random)
            {
                RandomListNode *oriRandom   =   oriNode->random;  
                cloneNode->random           =   oriRandom->next;//是原随机指针的next,不是原随机指针!
            }            
            //next oriNode
            oriNode   =   cloneNode->next;
        }

        //3.depart         
        //return:cloneHead
        RandomListNode *cloneHead   =   head->next;
        RandomListNode *cloneNode   =   cloneHead;  
        //oriNode Traversing from head
        oriNode     =   head;   
        while(oriNode)
        {
            //oriNode first
            oriNode->next   =   cloneNode->next;
            oriNode         =   oriNode->next; 
            //cloneNode second
            if(!oriNode)
                break;
            cloneNode->next =   oriNode->next;
            cloneNode       =   cloneNode->next;  
        }        
        return cloneHead;
    }  
};

二刷


 * 给定一个链表,每个节点包含一个额外增加的随机指针,该指针可以指向链表中的任何节点或空节点。
 * 
 * 要求返回这个链表的深度拷贝。 
 * 
 */
/**
 * Definition for singly-linked list with a random pointer.
 * struct RandomListNode {
 *     int label;
 *     RandomListNode *next, *random;
 *     RandomListNode(int x) : label(x), next(NULL), random(NULL) {}
 * };
 */
class Solution {
public:
    RandomListNode *copyRandomList(RandomListNode *head) 
    {
        if(!head)
            return head;

        //clone
        RandomListNode* oriNode=head;
        while(oriNode)
        {
            //copy
            RandomListNode* cloneNode=new RandomListNode(0);
            cloneNode->label=oriNode->label;
            cloneNode->next=oriNode->next;
            cloneNode->random=nullptr;
            //link
            oriNode->next=cloneNode;
            //next
            oriNode=cloneNode->next;            
        }
           
        //copy random
        oriNode=head;
        while(oriNode)
        {
            RandomListNode* cloneNode=oriNode->next;
            //copy
            if(oriNode->random)
            {
                cloneNode->random=oriNode->random->next;
            }
            //next
            oriNode=cloneNode->next;
        }
        
        //depart
        oriNode=head;
        RandomListNode* cloneNode=head->next;
        RandomListNode* cloneHead=cloneNode;//return
        
        while(oriNode)
        {
            oriNode->next=cloneNode->next;
            oriNode=oriNode->next;
            
            if(!oriNode)
                break;
            cloneNode->next=oriNode->next;
            cloneNode=cloneNode->next;
        }
        
        return cloneHead;
    }  
};

 


问题

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值