剑指offer--25. 复杂链表的复制

题目描述

输入一个复杂链表(每个节点中有节点值,以及两个指针,一个指向下一个节点,另一个特殊指针指向任意一个节点),返回结果为复制后复杂链表的head。(注意,输出结果中请不要返回参数中的节点引用,否则判题程序会直接返回空)

时间限制:1秒 空间限制:32768K 热度指数:274017
本题知识点: 链表

思路

一.时间复杂度应该是O(n)

  1. 先逐步复制结点,不包括random部分
  2. 新建map,存放新旧结点的地址
  3. 再根据map复制random部分
/*
struct RandomListNode {
    int label;
    struct RandomListNode *next, *random;
    RandomListNode(int x) :
            label(x), next(NULL), random(NULL) {
    }
};
*/
class Solution {
public:
    RandomListNode* Clone(RandomListNode* ph)
    {
        if(ph==NULL)
            return ph;
        RandomListNode* ph2=new RandomListNode(ph->label);//复制链表的头结点
        RandomListNode* ph22=ph2;
        RandomListNode* ph11=ph->next;
        map <RandomListNode*,RandomListNode*> v;				//存放新旧结点地址的对应关系
        while(ph11)//复制除了random部分的链表
        {
           RandomListNode* a=new RandomListNode(ph11->label);
            ph22->next=a;
            ph22=a;
            ph11=ph11->next;
        }
        ph22=ph2;
        ph11=ph;
        while(ph11)///在map里存放新旧结点地址
        {
            v[ph11]=ph22;
            ph11=ph11->next;
            ph22=ph22->next;
        }
        ph11=ph;
        ph22=ph2;
        while(ph11)//复制random部分
        {
            ph22->random=v[ph11->random];
            ph11=ph11->next;
            ph22=ph22->next;
        }
        return ph2;
    }
};

二.参考他人

  1. 复制结点信息(除了random和next),每复制一个就将其接在原结点后
  2. 复制random信息(每一个复制结点的random结点在原random结点的next处)
  3. 拆分两个链表(即复制next)
/*
struct RandomListNode {
    int label;
    struct RandomListNode *next, *random;
    RandomListNode(int x) :
            label(x), next(NULL), random(NULL) {
    }
};
*/
class Solution {
public:
    RandomListNode* Clone(RandomListNode* ph)
    {
        if(ph==NULL)
            return ph;
        RandomListNode* ph11=ph;
        while(ph11)//复制结点信息(除了random和next),每复制一个就将其接在原结点后
        {
            RandomListNode* a=new RandomListNode(ph11->label);
            a->next=ph11->next;
            ph11->next=a;
            ph11=a->next;
        }
        ph11=ph;
        while(ph11)//复制random信息(每一个复制结点的random结点在原random结点的next处)
        {
            if(ph11->random)
            ph11->next->random=ph11->random->next;
            ph11=ph11->next->next;
        }
        ph11=ph;
        RandomListNode* ph2=ph11->next;
        ph11->next=ph2->next;
        ph11=ph11->next;
        RandomListNode* ph22=ph2;
        while(ph11)//拆分两个链表(即复制next)
        {
            ph22->next=ph11->next;
            ph22=ph22->next;
            ph11->next=ph22->next;
            ph11=ph11->next;
        }
        return ph2;
    }
};
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值