1. 程式人生 > >Leetcode 002.兩數相加 [LeetCode] Add Two Numbers 兩個數字相加

Leetcode 002.兩數相加 [LeetCode] Add Two Numbers 兩個數字相加

1.題目描述

給出兩個 非空 的連結串列用來表示兩個非負的整數。其中,它們各自的位數是按照 逆序 的方式儲存的,並且它們的每個節點只能儲存 一位 數字。

如果,我們將這兩個數相加起來,則會返回一個新的連結串列來表示它們的和。

您可以假設除了數字 0 之外,這兩個數都不會以 0 開頭。

示例:

輸入:(2 -> 4 -> 3) + (5 -> 6 -> 4)
輸出:7 -> 0 -> 8
原因:342 + 465 = 807

2.易理解版本

2.1 解題思路

題中連結串列順序正好是低位到高位,先低位相加,有進位保持,下一位計算加上進位,直到最高位相加,如果有進位,生成新的結點儲存。

2.2 我的程式碼

//兩數相加
//沒有建立全新的連結串列,使用L1、L2中較長的儲存結果
class Solution {
public:
    ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {

        unsigned int count1 = 0, count2 = 0;//統計兩個連結串列長度
        unsigned int carry = 0; //進位

        while (l1 != NULL && l2 != NULL)
        {
            l1
->val = (l1->val + l2->val + carry) % 10; l2->val = (l1->val + l2->val + carry) % 10; //判斷有無進位 if ((l1->val + l2->val + carry) / 10 != 0) carry = 1; else carry = 0; // ((l1->val + l2->val + carry) / 10 != 0)?carry = 1 : carry = 0 ;
l1 = l1->next; l2 = l2->next; } if (l1 != NULL) { //L1更長,剩餘連結串列處理 while (l1 != NULL) { l1->val = (l1->val + carry) % 10; if ((l1->val + carry) / 10 != 0) carry = 1; else carry = 0; l1 = l1->next; } if (l1 == NULL && carry == 1) ListNode(1); return l1; } else { //L2更長,剩餘連結串列處理 while (l2 != NULL) { l2->val = (l2->val + carry) % 10; if ((l2->val + carry) / 10 != 0) carry = 1; else carry = 0; l2 = l2->next; } if (l2 == NULL && carry == 1) ListNode(1); return l2; } } };

 

3.簡潔版本

class Solution {
public:
    ListNode *addTwoNumbers(ListNode *l1, ListNode *l2) {
        ListNode *res = new ListNode(-1);//儲存結果
        ListNode *cur = res;
        int carry = 0;
        while (l1 || l2) {
            int n1 = l1 ? l1->val : 0;
            int n2 = l2 ? l2->val : 0;
            int sum = n1 + n2 + carry;
            carry = sum / 10;
            cur->next = new ListNode(sum % 10);
            cur = cur->next;
            if (l1) l1 = l1->next;
            if (l2) l2 = l2->next;
        }
        if (carry) cur->next = new ListNode(1);
        return res->next;
    }
};
//潛在問題:memory leak, ListNode *res = new ListNode(-1);沒有最後釋放。

4.用時更少的範例

//來源:Leetcode官網提交的答案
/*
* * Definition for singly-linked list. * struct ListNode { * int val; * ListNode *next; * ListNode(int x) : val(x), next(NULL) {} * }; */ //優化C++I/O提速 static const auto __ = []() { ios::sync_with_stdio(false); cin.tie(nullptr); return nullptr; }(); class Solution { public: ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) { ListNode* L_result = new ListNode(0); ListNode* a = l1; ListNode* b = l2; ListNode*cur = L_result; int carry = 0; while(a != NULL || b != NULL) { int val1 = a != NULL ? a->val : 0; int val2 = b != NULL ? b->val : 0; int sum = val1 + val2 + carry; carry = bool(sum / 10); cur->next = new ListNode(sum %10); //先判是否為空,再賦值 if(a != NULL) { a = a->next; } if(b != NULL) { b = b->next; } cur = cur->next; } if(carry) { cur->next = new ListNode(1); } return L_result->next; } };

 

參考資料:

1. [LeetCode] Add Two Numbers 兩個數字相加