题目信息

  • 时间: 2019-06-28

  • 题目链接:Leetcode

  • tag: 链表

  • 难易程度:中等

  • 题目描述:

    请实现 copyRandomList 函数,复制一个复杂链表。在复杂链表中,每个节点除了有一个 next 指针指向下一个节点,还有一个 random 指针指向链表中的任意节点或者 null。

示例1:

输入:head = [[7,null],[13,0],[11,4],[10,2],[1,0]]
输出:[[7,null],[13,0],[11,4],[10,2],[1,0]]

示例2:

输入:head = [[1,1],[2,1]]
输出:[[1,1],[2,1]]

提示

1.-10000 <= Node.val <= 10000
2.Node.random为null或指向链表中的节点
3.节点数目不超过1000

解题思路

本题难点

本题的意思是复制一个链表并返回,这个链表与一般链表不同的是多了一个 random 指针。

具体思路

这个复制过程可以分成两步:第一步是复制原始链表上的每个节点,并用next指针相连; 第二步是设置每个节点的random指针。

  • 复制节点:将原始链表的任意节点 N复制为新节点N',再把N'连接到 N的后面。即如果原始链表为A->B->C->D 则复制过后为A->A'->B->B'->C->C'->D->D'
  • 建立random连接: 如果原始链表上的节点 N 的random指针指向节点S,则它对应的复制节点N'的random指针指向节点S的复制节点S',也就是当前节点S的下一个节点。
  • 拆分链表:把这个长链表拆分成两个链表,把奇数位置的节点连接起来就是原始链表,把偶数位置的节点连接起来就是复制出来的链表。

代码

/*
// Definition for a Node.
class Node {
int val;
Node next;
Node random; public Node(int val) {
this.val = val;
this.next = null;
this.random = null;
}
}
*/
class Solution {
public Node copyRandomList(Node head) {
if(head == null){
return null;
}
//插入新节点
Node cur = head;
while(cur != null){
Node clone = new Node(cur.val);
clone.next = cur.next;
cur.next = clone;
cur = clone.next;
}
//建立random链接
cur = head;
while(cur != null){
Node clone = cur.next;
if(cur.random != null){
clone.random = cur.random.next;
}
cur = clone.next;
}
//拆分
cur = head;
Node cloneHead = head.next;
while(cur.next != null){
Node next = cur.next;
cur.next = next.next;
cur = next;
}
return cloneHead; }
}

复杂度分析:

  • 时间复杂度 O(N) : 链表长度为N,遍历所需时间。
  • 空间复杂度 O(1) :没有使用额外的空间保存已保存的节点。

其他优秀解答

解题思路

1.创建HashMap

2.复制结点值

3.复制指向(next,random)

代码

/*
// Definition for a Node.
class Node {
int val;
Node next;
Node random; public Node(int val) {
this.val = val;
this.next = null;
this.random = null;
}
}
*/
class Solution { //HashMap实现
public Node copyRandomList(Node head) {
HashMap<Node,Node> map = new HashMap<>(); //创建HashMap集合
Node cur=head;
//复制结点值
while(cur!=null){
//存储put:<key,value1>
map.put(cur,new Node(cur.val)); //顺序遍历,存储老结点和新结点(先存储新创建的结点值)
cur=cur.next;
}
//复制结点指向
cur = head;
while(cur!=null){
//得到get:<key>.value2,3
map.get(cur).next = map.get(cur.next); //新结点next指向同旧结点的next指向
map.get(cur).random = map.get(cur.random); //新结点random指向同旧结点的random指向
cur = cur.next;
}
//返回复制的链表
return map.get(head);
}
}

每日一题 - 剑指 Offer 35. 复杂链表的复制的更多相关文章

  1. 剑指 Offer 35. 复杂链表的复制

    剑指 Offer 35. 复杂链表的复制 Offer_35 题目详情 方法一 可以使用一个HashMap来存储旧结点和新结点的映射. 这种方法需要遍历链表两遍,因为需要首先知道映射关系才能求出next ...

  2. 【Java】 剑指offer(35) 复杂链表的复制

    本文参考自<剑指offer>一书,代码采用Java语言. 更多:<剑指Offer>Java实现合集   题目 请实现函数ComplexListNode* Clone(Compl ...

  3. 剑指offer——35复杂链表的复制

    这题很是巧妙. 突破了常规思维. 竟然可以把传入进来的链表和复制的链表链在一起.然后再算出slibling指针.最后在分离. 直接把空间复杂度变为O(1)了. 很巧妙,很实用. 题目: 请实现函数Co ...

  4. 力扣 - 剑指Offer 35.复杂链表的复制

    目录 题目 思路1 代码实现 思路2 代码实现 题目 请实现 copyRandomList 函数,复制一个复杂链表.在复杂链表中,每个节点除了有一个 next 指针指向下一个节点,还有一个 rando ...

  5. 【剑指Offer】复杂链表的复制 解题报告(Python)

    [剑指Offer]复杂链表的复制 解题报告(Python) 标签(空格分隔): 剑指Offer 题目地址:https://www.nowcoder.com/ta/coding-interviews 题 ...

  6. 《剑指offer》复杂链表的复制

    本题来自<剑指offer> 反转链表 题目: 思路: C++ Code: Python Code: 总结:

  7. Go语言实现:【剑指offer】复杂链表的复制

    该题目来源于牛客网<剑指offer>专题. 输入一个复杂链表(每个节点中有节点值,以及两个指针,一个指向下一个节点,另一个特殊指针指向任意一个节点),返回结果为复制后复杂链表的head.( ...

  8. 剑指Offer 25. 复杂链表的复制 (链表)

    题目描述 输入一个复杂链表(每个节点中有节点值,以及两个指针,一个指向下一个节点,另一个特殊指针指向任意一个节点),返回结果为复制后复杂链表的head.(注意,输出结果中请不要返回参数中的节点引用,否 ...

  9. 每日一题 - 剑指 Offer 49. 丑数

    题目信息 时间: 2019-07-03 题目链接:Leetcode tag:动态规划 小根堆 难易程度:中等 题目描述: 我们把只包含质因子 2.3 和 5 的数称作丑数(Ugly Number).求 ...

随机推荐

  1. 第八届蓝桥杯JavaB组省赛真题

    解题代码部分来自网友,如果有不对的地方,欢迎各位大佬评论 题目1.购物单 题目描述 小明刚刚找到工作,老板人很好,只是老板夫人很爱购物.老板忙的时候经常让小明帮忙到商场代为购物.小明很厌烦,但又不好推 ...

  2. Java实现 蓝桥杯 算法提高 矩阵翻转

    问题描述 Ciel有一个N*N的矩阵,每个格子里都有一个整数. N是一个奇数,设X = (N+1)/2.Ciel每次都可以做这样的一次操作:他从矩阵选出一个X*X的子矩阵,并将这个子矩阵中的所有整数都 ...

  3. Java实现 蓝桥杯 历届试题 连号区间数

    问题描述 小明这些天一直在思考这样一个奇怪而有趣的问题: 在1~N的某个全排列中有多少个连号区间呢?这里所说的连号区间的定义是: 如果区间[L, R] 里的所有元素(即此排列的第L个到第R个元素)递增 ...

  4. java实现第四届蓝桥杯剪格子

    剪格子 题目描述 如图p1.jpg所示,3 x 3 的格子中填写了一些整数. 我们沿着图中的红色线剪开,得到两个部分,每个部分的数字和都是60. 本题的要求就是请你编程判定:对给定的m x n 的格子 ...

  5. 你是项目经理了![IT项目经理成长晋升记1]

    凉爽的秋风,吹走了严热的夏季,K公司内部传来一个重磅消息.销售团队披荆斩棘,过三关斩六将,成功胜出,拿下公司在C省的首单,为C省市场的开拓打下了基础. K公司是2003年“非典”时期成立,坐落在美丽的 ...

  6. 容器技术之Docker私有镜像仓库docker-distribution

    在前边的博客中我们说到docker的架构由docker客户端.服务端以及仓库组成:docker仓库就是用来存放镜像的地方:其实docker registry我们理解为存放docker镜像仓库的仓库比较 ...

  7. .NET Web应用中为什么要使用async/await异步编程

    前言 什么是async/await? await和async是.NET Framework4.5框架.C#5.0语法里面出现的技术,目的是用于简化异步编程模型. async和await的关系? asy ...

  8. C# 反射与特性(十):EMIT 构建代码

    目录 构建代码 1,程序集(Assembly) 2,模块(Module) 3,类型(Type) 4,DynamicMethod 定义方法与添加 IL 前面,本系列一共写了 九 篇关于反射和特性相关的文 ...

  9. CGAL代码阅读跳坑指南

    CGAL代码阅读跳坑指南 整体框架介绍 CGAL中的算法和数据结构由它们使用的对象类型和操作参数化.它们可以处理满足特定语法和语义需求的任何具体模板参数.为了避免长参数列表,参数类型被收集到一个单独的 ...

  10. [noi.ac省选模拟赛20200606]赌怪

    题目   点这里看题目. 分析   先特判掉\(K=2\)的情况.   首先可以考虑到一个简单 DP :   \(f(i)\):前\(i\)张牌的最大贡献.   转移可以\(O(n^2)\)地枚举区间 ...