Java【手撕链表】LeetCode 2. “两数相加“, 图文详解思路分析 + 代码

文章目录

  • 前言
  • 一、两数相加
    • 1, 题目
    • 2, 思路分析
    • 3, 代码


前言

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


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

一、两数相加

1, 题目

OJ链接

题目给定的链表是倒序排列的, 这一点方便了我们进行遍历两个链表


2, 思路分析

本题的基本思路就是: 模拟两数加法的过程 + 构建新链表

  • 模拟两数相加: 需要考虑 “进位”, 因为题目规定每个结点只能存储一个数字, 所以形如 4 + 6 = 10, 7 + 7 = 14, 两数之和 > 9 的情况, 新结点中只能存储个位数, 那么十位上的 “1”, 就要加到后面的结点上
  • 构建新链表: 可以使用傀儡头结点的技巧, 每 new 出一个新结点就尾插到新的链表后面

准备工作如下:

  • 定义一个傀儡头结点 phead
  • 定义一个指针 cur, 指向 phead
  • 定义两个指针 cur1, cur2, 分别指向两个链表的头节点 l1, l2
  • 定义一个变量 carry, 表示进位

具体流程如下:

  • 1, carry = 2 + 5 = 7, carry / 10 = 0, 无需进位, 新结点的值就是 7

Java【手撕链表】LeetCode 2. “两数相加“, 图文详解思路分析 + 代码_第1张图片

  • 2, carry = 4 + 6 = 10, carry / 10 = 1, 需要进位 “1”, 新结点的值为 0 , 进位 1 留给下一个结点
    Java【手撕链表】LeetCode 2. “两数相加“, 图文详解思路分析 + 代码_第2张图片

  • 3, carry = 3 + 4 + 1 = 8 注意这里的 “1” 表示上一步的 “进位1” , carry / 10 = 0, 不需要进位, 新结点的值为 8Java【手撕链表】LeetCode 2. “两数相加“, 图文详解思路分析 + 代码_第3张图片

此时 cur1 和 cur 2 再往后走就是链表的末尾了, 但是还没完 ! ! ! 还有一个细节 ! ! !
假设: 两个链表末尾还有进位的情况, 如下图
Java【手撕链表】LeetCode 2. “两数相加“, 图文详解思路分析 + 代码_第4张图片
此时 cur1 和 cur2 也即将遍历到链表末尾, 但是有进位1, 所以还需要再给新链表 再尾插一个值为 1 的结点
Java【手撕链表】LeetCode 2. “两数相加“, 图文详解思路分析 + 代码_第5张图片
此时 cur1 和 cur2 都指向了 null, carry 也为 0, 这才算真正的结束

上述当 cur1 和 cur2 都遍历到 null 时, carry 是否为 1 的判断可以放到 while 循环中, 也可以最后单独做一个 if 判断

最终返回新链表的头结点, 返回 phead.next 即可


3, 代码

	public ListNode addTwoNumbers(ListNode l1, ListNode l2) {
        if(l1 == null || l2 == null) {
            return null;
        }
        ListNode phead = new ListNode(0); // 傀儡头结点
        ListNode cur1 = l1;
        ListNode cur2 = l2;
        ListNode cur = phead;
        int carry = 0; // 表示进位
        while(cur1 != null || cur2 != null || carry != 0) {
            if(cur1 != null) {
                carry += cur1.val;
                cur1 = cur1.next;
            }
            if(cur2 != null) {
                carry += cur2.val;
                cur2 = cur2.next;
            }
            cur.next = new ListNode(carry % 10);
            carry /= 10; // 表示进位
            cur = cur.next;
        }
        return phead.next;
    }

你可能感兴趣的:(OJ题,链表,leetcode,java,两数相加,傀儡节点)