leetcode刷题日记——2.两数相加

给你两个 非空 的链表,表示两个非负的整数。它们每位数字都是按照 逆序 的方式存储的,并且每个节点只能存储 一位 数字。
请你将两个数相加,并以相同形式返回一个表示和的链表。
你可以假设除了数字 0 之外,这两个数都不会以 0 开头。


示例

输入:l1 = [2,4,3], l2 = [5,6,4]
输出:[7,0,8]
解释:342 + 465 = 807.

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/add-two-numbers
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

1、朴素解法

数字在链表中是倒序放置的,则可以从链表的头节点开始逐个相加,使用中间变量存储进位信息,加入结果链表中。
时间复杂度:O(max(m, n)),m、n为两个链表的长度
空间复杂度:消耗常数级的空间,空间复杂度为O(1)

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode() {}
 *     ListNode(int val) { this.val = val; }
 *     ListNode(int val, ListNode next) { this.val = val; this.next = next; }
 * }
 */
class Solution {
    public ListNode addTwoNumbers(ListNode l1, ListNode l2) {
        ListNode ret = new ListNode();
        ListNode ptr1 = l1;
        ListNode ptr2 = l2;
        ListNode ptr = ret;
        int temp = 0;
        while(ptr1 != null || ptr2 != null){
            ListNode add = new ListNode();
            ptr.next = add;
            if(ptr1 != null && ptr2 != null){
                add.val = (ptr1.val + ptr2.val) % 10 + temp;
                if(add.val >= 10){
                    temp = add.val / 10;
                    add.val %= 10;
                }else{
                    temp = (ptr1.val + ptr2.val) / 10;
                }
            }else if(ptr1 == null && ptr2 != null){
                add.val = ptr2.val + temp;
                if(add.val >= 10){
                    temp = add.val / 10;
                    add.val %= 10;
                }else{
                    temp = 0;
                }
            }else{
                add.val = ptr1.val + temp;
                if(add.val >= 10){
                    temp = add.val / 10;
                    add.val %= 10;
                }else{
                    temp = 0;
                }
            }
            ptr = add;
            if(ptr1 != null){
                ptr1 = ptr1.next;
            }
            if(ptr2 != null){
                ptr2 = ptr2.next;
            }
        }
        if(temp != 0){
            ListNode last = new ListNode();
            ptr.next = last;
            last.val = temp;
            ptr = last;
        }
        return ret.next;
    }
}

2、递归解法

对于链表操作可以考虑递归解法。每一次操作取两个节点的值相加,获得当前节点的值及进位值,然后返回下一个节点。
时间复杂度:O(max(m,n)),m、n为链表长度
空间复杂度:空间复杂度与递归深度相关,O(max(m, n))

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode() {}
 *     ListNode(int val) { this.val = val; }
 *     ListNode(int val, ListNode next) { this.val = val; this.next = next; }
 * }
 */
class Solution {
    public ListNode addTwoNumbers(ListNode l1, ListNode l2) {
        return recursive(l1, l2, 0);
    }

    ListNode recursive(ListNode listNodeA, ListNode listNodeB, int carry){
        int valA = listNodeA == null? 0 : listNodeA.val;
        int valB = listNodeB == null? 0 : listNodeB.val;
        int num = (valA + valB + carry) % 10;
        if(listNodeA == null && listNodeB == null){
            return carry == 0? null : new ListNode(carry);
        }
        ListNode nextNodeA = listNodeA == null? null : listNodeA.next;
        ListNode nextNodeB = listNodeB == null? null : listNodeB.next;
        carry = (valA + valB + carry) / 10;
        return new ListNode(num, recursive(nextNodeA, nextNodeB, carry));
    }
}

你可能感兴趣的:(leetcode刷题日记——2.两数相加)