题意

You are given two non-empty linked lists representing two non-negative integers. The digits are stored in reverse order and each of their nodes contain a single digit. Add the two numbers and return it as a linked list.

You may assume the two numbers do not contain any leading zero, except the number 0 itself.

给你两个非空链表,每个节点存储一位值,是反过来存储的。用同样的存储方式返回他们的和。

思路

直接模拟,高精度加,考察链表。裸题。
时间复杂度 O ( m a x ( L 1 , L 2 ) ) O(max(L1,L2)) O(max(L1,L2))

源码

class Solution {
    public ListNode addTwoNumbers(ListNode l1, ListNode l2) {
        ListNode head = null;
        ListNode r = null;
        int t = 0;
        int s;
        while (l1 != null && l2 != null) {
            s = l1.val + l2.val + t;
            l1 = l1.next;
            l2 = l2.next;
            t = s/10; s %= 10;
            if (r == null) {
                r = new ListNode(s);
                head = r;
            } else {
                r.next = new ListNode(s);
                r = r.next;
            }
        }
        ListNode rest;
        if (l1 != null)
            rest = l1;
        else if (l2 != null)
            rest = l2;
        else {
            // case 3
            if (t > 0)
                r.next = new ListNode(t);
            return head;
        }
        while (rest != null) {
            s = rest.val  + t;
            rest = rest.next;
            t = s/10; s %= 10;
            r.next = new ListNode(s);
            r = r.next;
        }
        if (t > 0)
            r.next = new ListNode(t);
        return head;
    }
}
class Solution {
   public ListNode addTwoNumbers(ListNode l1, ListNode l2) {
       ListNode head = null;
       ListNode r = null;
       int t = 0;
       int s;
       while (l1 != null || l2 != null || t > 0) {
           s = (l1 == null ? 0 : l1.val) + (l2 == null ? 0 : l2.val) + t;
           l1 = l1 == null ? null : l1.next;
           l2 = l2 == null ? null : l2.next;
           t = s/10; s %= 10;
           if (r == null) {
               r = new ListNode(s);
               head = r;
           } else {
               r.next = new ListNode(s);
               r = r.next;
           }
       }
       return head;
   }
}
class Solution {
    public ListNode addTwoNumbers(ListNode l1, ListNode l2) {
        ListNode head,r;
        head = r = new ListNode(0);
        int t = 0;
        int s;
        while (l1 != null || l2 != null || t > 0) {
            s = (l1 == null ? 0 : l1.val) + (l2 == null ? 0 : l2.val) + t;
            l1 = (l1 == null ? null : l1.next);
            l2 = (l2 == null ? null : l2.next);
            t = s/10;
            r = r.next = new ListNode(s%10);
        }
        return head.next;
    }
}

时间比较及分析

结果比较

3次的结果分别是
Runtime: 31 ms, faster than 38.95% of Java online submissions for Add Two Numbers.
Memory Usage: 43.3 MB, less than 100.00% of Java online submissions for Add Two Numbers.

Runtime: 23 ms, faster than 67.88% of Java online submissions for Add Two Numbers.
Memory Usage: 48.1 MB, less than 100.00% of Java online submissions for Add Two Numbers.

Runtime: 21 ms, faster than 92.00% of Java online submissions for Add Two Numbers.
Memory Usage: 47.9 MB, less than 100.00% of Java online submissions for Add Two Numbers.

分析

第一次提交只有38.95%不到60%,由于时间复杂度已经是线性了,而且理论上复杂度不能再低了,因此推测应该是——
我人丑代码丑,自带大常数。

于是我想了一下,改成了版本2.过60%了。
我觉得就可以了。
^_^ ? ^_^
之后去discussion看了一下大佬的代码,于是仿照着大佬的再写了一下,优化了2ms,居然提升到了90%多。
常数优化,性能优化真是太恐怖了。
个人觉得,
这种性能优化意义不大。
这种性能优化意义不大。
这种性能优化意义不大。