给大家推荐一道leetcode上的面试题,这道题的详细解说在《剑指offer》的P149页有思路解说。假设你手头有这本书。建议翻阅。

题目链接 here

A linked list is given such that each node contains an additional random pointer which could point to any node in the list or null.

Return a deep copy of the list.

RandomList中。每一个节点不光有一个next指针。并且每一个链表节点都有一个random指针。随机指向链表中的一个节点,让你复制这个链表,节点的C++定义例如以下。

/**
* 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) {}
* };
*/

看到这个题目,预计非常多人的第一反应是,先把这个单链表复制出来,然后挨个找random指向的节点。细致想想这样效率非常低。复制链表非常快。但确定每一个节点的random指针就不easy了,用这样的方法的话。每找一个random指针,都必须遍历一次链表。时间复杂度O(n^2)。

可能也有人可能会想到时间换空间的方法,用hash把时间复杂度降到O(n)。

当然,还有更省时省空间的方法。

大概思路就是,在原链表的基础上,把每一个节点复制一份加的原来节点的后面,然后设置好新节点random指针,在把全部的新节点从原链表中分离出来。构成一个新链表,这个链表就是我们要的原链表的拷贝。

以下有三个函数,第一个明显就是复制新节点并把其增加到被复制节点的后面。第二个。由于新节点的random指针还是指向旧节点的。要把它指向新节点。非常easy,由于每一个节点的新节点都是在原来的节点之后的。

第三个函数。把新节点从原链表中抽离,构成一个新链表。

这样的方法的优点就是。时间复杂度仅仅有O(n),并且我们不须要额外的空间。

class Solution {
public:
void CloneNode(RandomListNode *head) {
RandomListNode * p = head;
while (NULL != p) {
RandomListNode * CloneNode = new RandomListNode(p->label);
CloneNode->next = p->next;
CloneNode->random = p->random;
p->next = CloneNode;
p = CloneNode->next;
}
} void ConnectRandomNode(RandomListNode * head) {
RandomListNode * p = head;
while (NULL != p) {
RandomListNode *pclone = p->next;
if (NULL != pclone->random) {
pclone->random = pclone->random->next;
}
p = pclone->next;
}
}
RandomListNode *copyRandomList(RandomListNode *head) {
if (NULL == head)
return head;
CloneNode(head);
ConnectRandomNode(head);
RandomListNode *pnode = head;
RandomListNode *pclonehead = pnode->next;
RandomListNode *pclonenode = pnode->next;
while (NULL != pnode) {
pnode->next = pclonenode->next;
pnode = pnode->next;
if (NULL != pnode){
pclonenode->next = pnode->next;
pclonenode = pclonenode->next;
}
}
return pclonehead;
} };

Leetcode Copy List with Random Pointer(面试题推荐)的更多相关文章

  1. [LeetCode] Copy List with Random Pointer 拷贝带有随机指针的链表

    A linked list is given such that each node contains an additional random pointer which could point t ...

  2. [leetcode]Copy List with Random Pointer @ Python

    原题地址:https://oj.leetcode.com/problems/copy-list-with-random-pointer/ 题意: A linked list is given such ...

  3. LeetCode——Copy List with Random Pointer

    A linked list is given such that each node contains an additional random pointer which could point t ...

  4. LeetCode——Copy List with Random Pointer(带random引用的单链表深拷贝)

    问题: A linked list is given such that each node contains an additional random pointer which could poi ...

  5. Leetcode Copy List with Random Pointer

    A linked list is given such that each node contains an additional random pointer which could point t ...

  6. [Leetcode] Copy list with random pointer 对带有任意指针的链表深度拷贝

    A linked list is given such that each node contains an additional random pointer which could point t ...

  7. LeetCode – Copy List with Random Pointer

    A linked list is given such that each node contains an additional random pointer which could point t ...

  8. [LeetCode]Copy List with Random Pointer &Clone Graph 复杂链表的复制&图的复制

    /** * Definition for singly-linked list with a random pointer. * struct RandomListNode { * int label ...

  9. [Leetcode Week17]Copy List with Random Pointer

    Copy List with Random Pointer 题解 原创文章,拒绝转载 题目来源:https://leetcode.com/problems/copy-list-with-random- ...

随机推荐

  1. How to use transparent PNG icons with Delphi ImageList

    http://www.aha-soft.com/faq/delphi-imagelist-png.htm Query: "Embarcadero Delphi ImageList does ...

  2. 关闭OOMER

    http://www.cnblogs.com/itfriend/archive/2011/12/14/2287160.html http://blog.csdn.net/gugemichael/art ...

  3. 让mbox支持up效果

    <!doctype html> <html> <head> <meta charset="utf-8"> <title> ...

  4. 在Mac中设置Ctrl+C/V进行复制/粘贴

    从Windows世界走入Mac世界,最让不习惯的是在Mac中“复制/粘贴”的快捷键是Command+C/V.而且Command键与C/V键靠得太近,只能用大拇指与食指进行操作,也让人不习惯.再加上远程 ...

  5. 使用 JMeter 完成常用的压力测试

    国内私募机构九鼎控股打造APP,来就送 20元现金领取地址:http://jdb.jiudingcapital.com/phone.html内部邀请码:C8E245J (不写邀请码,没有现金送)国内私 ...

  6. python使用游标访问数据

    游标是一种数据访问对象,可用于在表中迭代一组行或者向表中插入新行.游标有三种形式:搜索.插入或更新.游标通常用于读取现有几何和写入新几何. 每种类型的游标均由对应的 ArcPy 函数(SearchCu ...

  7. 跨域策略文件crossdomain.xml

    Web站点通过crossdomain.xml文件(放于站点根目录)配置提供允许的域跨域访问本域内容的权限 以土豆的为例: <cross-domain-policy> <allow-a ...

  8. Workflow:采用坐标变换(移动和旋转)画箭头

    背景 流程设计器的连线部分需要画一个箭头代表连接的方向,下图是期望的效果: 刚开始我准备采用三角函数(sin和cos)来计算三角的坐标,实现的过程真不爽(有兴趣的朋友可以试试),就在完工的时候,突然想 ...

  9. pytest文档1-环境准备与入门

    前言 首先说下为什么要学pytest,在此之前相信大家已经掌握了python里面的unittest单元测试框架,那再学一个框架肯定是需要学习时间成本的. 刚开始我的内心是拒绝的,我想我用unittes ...

  10. [Linux] Ubuntu下的文件比较工具--meld

    在ubuntu中需要比较文件的差异,于是安装meld apt-get install meld 安装完后,在/usr/bin/下找到meld,然后发送到桌面上, 或者在命令行执行meld命令 打开后选 ...