Java【手撕链表】LeetCode 143. “重排链表“, 图文详解思路分析 + 代码

news2024/12/30 1:58:06

文章目录

  • 前言
  • 一、两数相加
    • 1, 题目
    • 2, 思路分析
      • 2,1 找到中间结点
      • 2.2, 逆序后半段链表
      • 2.3, 合并两个链表
    • 3, 代码


前言

各位读者好, 我是小陈, 这是我的个人主页, 希望我的专栏能够帮助到你:
📕 JavaSE基础: 基础语法, 类和对象, 封装继承多态, 接口, 综合小练习图书管理系统等
📗 Java数据结构: 顺序表, 链表, 堆, 二叉树, 二叉搜索树, 哈希表等
📘 JavaEE初阶: 多线程, 网络编程, TCP/IP协议, HTTP协议, Tomcat, Servlet, Linux, JVM等(正在持续更新)


对于链表题, 常用的技巧和操作是: 头插, 尾插, 快慢双指针, 傀儡节点

一、两数相加

1, 题目

OJ链接

题目规定不能改变链表里的值, 而是真正交换链表节点


2, 思路分析

首先, 按照题意画出重排之后的链表, 观察原链表和重排之后的链表有什么变化
在这里插入图片描述
只看橙色结点, 发现后半段链表是逆序

至此 本题的思路就非常清晰了

  • 1, 找到中间节点(快慢双指针)
  • 2, 逆序后半段链表(傀儡头节点 + 头插)
  • 3, 合并两个链表(傀儡头结点 + 双指针)

注意本题没有返回值, 所以第三步操作之后不是返回新的头结点, 而是要修改原链表的头结点 head 之后的结点的指向

2,1 找到中间结点

  • 1, 定义 slow 和 fast 两个指针, 起始位置都指向头结点
  • 2, slow 每次走一步, fast 每次走两步
  • 3, 当 fast 为 null 或 fast.next 为 null 时退出循环
    在这里插入图片描述

如果有奇数个结点, slow 刚好是中间结点, 如果是偶数个结点, slow 是偏右的中间节点


2.2, 逆序后半段链表

  • 1, 定义一个傀儡节点 pHead
  • 2, 定义一个 target 指针, target 就指向刚才的 slow
  • 3, 定义一个 next 指针, 记录 target 的下一个结点
  • 4, 循环遍历后半段链表, 依次头插到 pHead 所在的链表

在这里插入图片描述

**加粗样式**
在这里插入图片描述
此时 target 为 null, 逆序完成, 退出循环

这里有个 bug ! 在循环逆序链表之前应该先断开原链表的前半段和后半段
否则逆序完成之后, 原链表并没有断开, 再执行第三步 (合并两个链表) 时就会发生死循环!
在这里插入图片描述
所以在第一步时应该定义一个 prev 指针, 记录 slow 结点的前一个结点, 找到中间结点后, 令 prev.next = null


2.3, 合并两个链表

  • 1, 定义一个傀儡节点 ret
  • 2, 定义一个 cur1 指针, 指向原链表头结点 head
  • 3, 定义一个 cur2 指针, 指向逆序后的链表的头结点
  • 4, 定义一个 cur3 指针, 指向 ret

1, cur1 尾插到 cur3 后面
在这里插入图片描述

(此时 1 这个结点还指向 2 ), cur2 尾插到 cur3 后面

在这里插入图片描述


2, (此时 6 这个结点还指向 5 ), cur1 尾插到 cur3 后面,

在这里插入图片描述

(此时 2 这个结点还指向 3 ), cur2 尾插到 cur3 后面

在这里插入图片描述


3, (此时 5 这个结点还指向 4 ), cur1 尾插到 cur3 后面
在这里插入图片描述

cur2 尾插到 cur3 后面
在这里插入图片描述


4, 得到整个链表, 此时 head 结点还在, 并且 head 之后的结点链表结构已经被修改成功
在这里插入图片描述

在一次循环中, 先尾插 cur1, 再尾插 cur2, 循环条件设为 cur1 != null 即可

因为 : 如果链表是偶数个结点, 链表前半段和后半段长度相同, 如果链表是奇数个结点, 链表前半段比后半段少一个结点, 但没关系, 尾插时不会改变结点的的 next 域


3, 代码

	public void reorderList(ListNode head) {
        if(head == null || head.next == null) {
            return;
        }
        // 1, 找到中间节点
        ListNode slow = head;
        ListNode fast = slow;
        ListNode prev = head;
        while(fast != null && fast.next != null) {
            prev = slow;
            slow = slow.next;
            fast = fast.next.next;
        }
        ListNode target = slow;
        prev.next = null;
        ListNode phead = new ListNode(0);
        ListNode cur = phead;
        
        // 2, 逆序后半个链表
        while(target != null) {
            ListNode next = target.next;
            target.next = cur.next;
            cur.next = target;
            target = next;
        }
        ListNode cur1 = head;
        ListNode cur2 = phead.next;
        ListNode ret = new ListNode(0);
        ListNode cur3 = ret;
        
        // 3, 合并链表
        while(cur1 != null){
            cur3.next = cur1;
            cur3 = cur3.next;
            cur1 = cur1.next;

            cur3.next = cur2;
            cur3 = cur3.next;
            cur2 = cur2.next;
        }
    }

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1050917.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

springcloud之自我介绍

写在前面 在这篇文章 中我们分析了单体应用的问题,以及用来解决这些问题的解决的方案微服务,并接着看了微服务需要考虑的各种,如服务调用,负载均衡,服务治理,链路追踪,分布式事务,等…

Konva离屏缓存

前言 cache实例方法定义在Node基类上,通过该方法可以实现图形缓存,在Konva中Stage、Layer、Group、Shape等所有容器类和图形类都直接或间接继承了Node基类,故而都可以使用缓存方法。本篇文章就是探讨Konva背后的缓存机制,版本是v…

300以内的开放耳机哪款好、300以内神级耳机推荐

开放式耳机基于不入耳、长久舒适佩戴的特点,在 2023 年迎来了增长爆发期。基于其开放式不入耳设计,佩戴时耳道会持续保持畅通状态,减少了对耳朵的压力,既能在通话或欣赏音乐时提供清晰的声音,又能让周围的环境声音透过…

Scala第二章节

Scala第二章节 scala总目录 章节目标 掌握变量, 字符串的定义和使用掌握数据类型的划分和数据类型转换的内容掌握键盘录入功能理解Scala中的常量, 标识符相关内容 1. 输出语句和分号 1.1 输出语句 方式一: 换行输出 格式: println(里边写你要打印到控制台的数据);方式二…

【Java 进阶篇】MySQL多表查询之子查询详解

在数据库查询中,多表查询是一项非常常见且重要的任务。它允许我们从多个相关联的表中检索和组合数据,以满足各种复杂的查询需求。在多表查询中,子查询是一种强大的工具,用于在查询中嵌套另一个查询。本文将深入探讨MySQL中的子查询…

直播软件开发技巧:7个实时视频传输和弹幕功能的关键步骤

近年来,随着直播行业的快速崛起,直播软件的开发变得越来越重要。直播软件的成功不仅依赖于稳定的实时视频传输,还需要强大的弹幕功能来提升用户体验。作为直播软件开发领域的专家,我将与您分享七个关键步骤,帮助您掌握…

python使用mitmproxy和mitmdump抓包在电脑上抓包

mitmproxy是一个中间人角色,供python抓包使用。 本机环境:win10 64位,python3.10.4。首先安装mitmproxy,参考我的文章 记录一下python2和python3在同一台电脑上共存使用并安装各自的库以及各自在pycharm中使用的方法-CSDN博客 一…

SimpleCG文字输出基础

前言 前面已经介绍了图形绘制,本篇将介绍简单的文字输出操作方法。其实文字在计算机中也是作为图形处理的,只是一种特殊的图形,是按固定预设字模图形来绘制的,称为字体。文字输出就是按文字所在字体中的对应图形绘制出来&#xff…

【golang】调度系统之整体介绍

调度系列 调度系列之goroutine 调度系列之m 调度系列之p 调度系列之sysmon 前面几篇对调度体系的G、M、P、sysmon分别进行了介绍。拆分的介绍有助于聚焦单一的角色,比较快地建立认识,同时也能更深入细节,但是不足以建立全局的认知。本篇在前面…

C理解(五):编译,链接库,宏,关键字,变量

编译 编译过程 文件.c->(预处理)->文件.i->(编译)->文件.S->(汇编)->文件.o->(链接)->elf程序 预处理 内容:加载头文件(#include),清除注释(//,./*),替换条件编译(#if #elif #endif #ifdef),替换宏定义(#define) …

[杂谈]-ESP32中的无线通信协议

ESP32中的无线通信协议 文章目录 ESP32中的无线通信协议1、ESP32 无线通信协议简介2、Bluetooth Low Energy (BLE)3、**Bluetooth Classic**4、**ESP-NOW**5、Wi-Fi(客户端-服务器通信协议)6、MQTT7、**LoRa**8、**GSM/GPRS/LTE**9、总结 ESP32是一个基于…

BL808学习日志-0-概念理解

一、主核心的介绍 1.三个核心在FREERTOS系统中相互独立,各负责各自的外设和程序;其中M0和LP核心在一个总线上,D0单独在一个总线上,两个总线使用AXI4.0(??)通讯? CPU0(M0)-E907架构,320MHz; CPU1(LP)-E9…

基于微信小程序的高校宿舍管理系统设计与实现(亮点:选择宿舍、宿舍评分、宿舍报修)

文章目录 前言系统主要功能:具体实现截图论文参考详细视频演示为什么选择我自己的网站自己的小程序(小蔡coding)有保障的售后福利 代码参考源码获取 前言 💗博主介绍:✌全网粉丝10W,CSDN特邀作者、博客专家、CSDN新星计…

【中秋节快乐】Matplotlib:3d绘图合集

目录 一、环境介绍 二、Matplotlib绘图(3d) 0. 设置中文字体 1. 3D线框图(3D Wireframe Plot) 2. 3D散点图(3D Scatter Plot) 3. 3D条形图(3D Bar Plot) 4. 3D曲面图&#xff0…

微信小游戏从零到上线系列文章整理,建议收藏

引言 本系列是《从零开始开发贪吃蛇小游戏到上线系列》,欢迎大家关注分享收藏订阅。 大家中秋快乐,我是亿元程序员,一位有着8年游戏行业经验的主程。前面笔者给大家讲解了微信小游戏如何从零到上线的流程。可能很多小伙伴都还没有看到。 本…

【深度学习_TensorFlow】卷积神经网络(CNN)

写在前面 这篇文章的行文思路如下: 先根据视频了解卷积和卷积神经网络的整体框架 接着了解卷积神经网络构建过程中的一些重要操作,包括内积、填充、池化。 然后介绍卷积层如何实现。 最后用卷积神经网络的开山之作(LeNet-5)来…

22 mysql range 查询

前言 这里主要是 探究一下 explain $sql 中各个 type 诸如 const, ref, range, index, all 的查询的影响, 以及一个初步的效率的判断 这里会调试源码来看一下 各个类型的查询 需要 lookUp 的记录 以及 相关的差异 此系列文章建议从 mysql const 查询 开始看 测试表结构…

奶茶果饮外卖配送小程序商城的作用是什么

奶茶果饮商家众多,有加盟品牌也有独立自创品牌或小店等,奶茶果饮已经成为众多年轻人群体喜爱的饮品,在实际消费方面,普遍以到店外卖为主,市场需求较高,但同样的竞争压力也不小。 同行竞争激烈,…

【教学类-35-03】学号+姓名+班级(小3班)学号字帖(A4竖版2份)

图片展示: 背景需求: 本周排到小3班,还没有来得及设计小班主题活动书的内容,于是就把小2班的学号字帖微调一下,做一份竖版2份的学号字帖。 让幼儿熟悉自己的学号,让我也熟悉幼儿的名字和学号 材料准备: 描字写&#…

Excel 使用 ctrl + E 快捷键进行数据提取、合并、添加前后缀等操作

使用组合键【Ctrl E】,你可以对数据进行合并、数据提取、添加前后缀等操作。 合并 提取 加前后缀或单位