<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                合規國際互聯網加速 OSASE為企業客戶提供高速穩定SD-WAN國際加速解決方案。 廣告
                # 0002. 兩數相加 ## 題目地址(2. 兩數相加) <https://leetcode-cn.com/problems/add-two-numbers/> ## 題目描述 ``` <pre class="calibre18">``` 給出兩個 非空 的鏈表用來表示兩個非負的整數。其中,它們各自的位數是按照 逆序 的方式存儲的,并且它們的每個節點只能存儲 一位 數字。 如果,我們將這兩個數相加起來,則會返回一個新的鏈表來表示它們的和。 您可以假設除了數字 0 之外,這兩個數都不會以 0 開頭。 示例: 輸入:(2 -> 4 -> 3) + (5 -> 6 -> 4) 輸出:7 -> 0 -> 8 原因:342 + 465 = 807 ``` ``` ## 前置知識 - 鏈表 ## 公司 - 阿里 - 百度 - 騰訊 ## 思路 設立一個表示進位的變量 carried,建立一個新鏈表, 把輸入的兩個鏈表從頭往后同時處理,每兩個相加,將結果加上 carried 后的值作為一個新節點到新鏈表后面。 ![](https://img.kancloud.cn/cd/2a/cd2a9ec008332c2913cbe3e9c5b2737e_953x528.gif) (圖片來自: <https://github.com/MisterBooo/LeetCodeAnimation>) ## 關鍵點解析 1. 鏈表這種數據結構的特點和使用 2. 用一個 carried 變量來實現進位的功能,每次相加之后計算 carried,并用于下一位的計算 ## 代碼 - 語言支持:JS,C++ JavaScript: ``` <pre class="calibre18">``` <span class="hljs-title">/** * Definition for singly-linked list. * function ListNode(val) { * this.val = val; * this.next = null; * } */</span> <span class="hljs-title">/** * @param {ListNode} l1 * @param {ListNode} l2 * @return {ListNode} */</span> <span class="hljs-keyword">var</span> addTwoNumbers = <span class="hljs-function"><span class="hljs-keyword">function</span> (<span class="hljs-params">l1, l2</span>) </span>{ <span class="hljs-keyword">if</span> (l1 === <span class="hljs-params">null</span> || l2 === <span class="hljs-params">null</span>) <span class="hljs-keyword">return</span> <span class="hljs-params">null</span>; <span class="hljs-title">// 使用dummyHead可以簡化對鏈表的處理,dummyHead.next指向新鏈表</span> <span class="hljs-keyword">let</span> dummyHead = <span class="hljs-keyword">new</span> ListNode(<span class="hljs-params">0</span>); <span class="hljs-keyword">let</span> cur1 = l1; <span class="hljs-keyword">let</span> cur2 = l2; <span class="hljs-keyword">let</span> cur = dummyHead; <span class="hljs-title">// cur用于計算新鏈表</span> <span class="hljs-keyword">let</span> carry = <span class="hljs-params">0</span>; <span class="hljs-title">// 進位標志</span> <span class="hljs-keyword">while</span> (cur1 !== <span class="hljs-params">null</span> || cur2 !== <span class="hljs-params">null</span>) { <span class="hljs-keyword">let</span> val1 = cur1 !== <span class="hljs-params">null</span> ? cur1.val : <span class="hljs-params">0</span>; <span class="hljs-keyword">let</span> val2 = cur2 !== <span class="hljs-params">null</span> ? cur2.val : <span class="hljs-params">0</span>; <span class="hljs-keyword">let</span> sum = val1 + val2 + carry; <span class="hljs-keyword">let</span> newNode = <span class="hljs-keyword">new</span> ListNode(sum % <span class="hljs-params">10</span>); <span class="hljs-title">// sum%10取模結果范圍為0~9,即為當前節點的值</span> carry = sum >= <span class="hljs-params">10</span> ? <span class="hljs-params">1</span> : <span class="hljs-params">0</span>; <span class="hljs-title">// sum>=10,carry=1,表示有進位</span> cur.next = newNode; cur = cur.next; <span class="hljs-keyword">if</span> (cur1 !== <span class="hljs-params">null</span>) { cur1 = cur1.next; } <span class="hljs-keyword">if</span> (cur2 !== <span class="hljs-params">null</span>) { cur2 = cur2.next; } } <span class="hljs-keyword">if</span> (carry > <span class="hljs-params">0</span>) { <span class="hljs-title">// 如果最后還有進位,新加一個節點</span> cur.next = <span class="hljs-keyword">new</span> ListNode(carry); } <span class="hljs-keyword">return</span> dummyHead.next; }; ``` ``` C++ > C++代碼與上面的 JavaScript 代碼略有不同:將 carry 是否為 0 的判斷放到了 while 循環中 ``` <pre class="calibre18">``` <span class="hljs-title">/** * Definition for singly-linked list. * struct ListNode { * int val; * ListNode *next; * ListNode(int x) : val(x), next(NULL) {} * }; */</span> <span class="hljs-keyword">class</span> Solution { <span class="hljs-keyword">public</span>: <span class="hljs-function">ListNode* <span class="hljs-title">addTwoNumbers</span><span class="hljs-params">(ListNode* l1, ListNode* l2)</span> </span>{ ListNode* ret = <span class="hljs-params">nullptr</span>; ListNode* cur = <span class="hljs-params">nullptr</span>; <span class="hljs-keyword">int</span> carry = <span class="hljs-params">0</span>; <span class="hljs-keyword">while</span> (l1 != <span class="hljs-params">nullptr</span> || l2 != <span class="hljs-params">nullptr</span> || carry != <span class="hljs-params">0</span>) { carry += (l1 == <span class="hljs-params">nullptr</span> ? <span class="hljs-params">0</span> : l1->val) + (l2 == <span class="hljs-params">nullptr</span> ? <span class="hljs-params">0</span> : l2->val); <span class="hljs-keyword">auto</span> temp = <span class="hljs-keyword">new</span> ListNode(carry % <span class="hljs-params">10</span>); carry /= <span class="hljs-params">10</span>; <span class="hljs-keyword">if</span> (ret == <span class="hljs-params">nullptr</span>) { ret = temp; cur = ret; } <span class="hljs-keyword">else</span> { cur->next = temp; cur = cur->next; } l1 = l1 == <span class="hljs-params">nullptr</span> ? <span class="hljs-params">nullptr</span> : l1->next; l2 = l2 == <span class="hljs-params">nullptr</span> ? <span class="hljs-params">nullptr</span> : l2->next; } <span class="hljs-keyword">return</span> ret; } }; ``` ``` **復雜度分析** - 時間復雜度:O(N)O(N)O(N) - 空間復雜度:O(1)O(1)O(1) ## 拓展 通過單鏈表的定義可以得知,單鏈表也是遞歸結構,因此,也可以使用遞歸的方式來進行 reverse 操作。 > 由于單鏈表是線性的,使用遞歸方式將導致棧的使用也是線性的,當鏈表長度達到一定程度時,遞歸會導致爆棧,因此,現實中并不推薦使用遞歸方式來操作鏈表。 ### 描述 1. 將兩個鏈表的第一個節點值相加,結果轉為 0-10 之間的個位數,并設置進位信息 2. 將兩個鏈表第一個節點以后的鏈表做帶進位的遞歸相加 3. 將第一步得到的頭節點的 next 指向第二步返回的鏈表 ### C++實現 ``` <pre class="calibre18">``` <span class="hljs-title">// 普通遞歸</span> <span class="hljs-keyword">class</span> Solution { <span class="hljs-keyword">public</span>: <span class="hljs-function">ListNode* <span class="hljs-title">addTwoNumbers</span><span class="hljs-params">(ListNode* l1, ListNode* l2)</span> </span>{ <span class="hljs-keyword">return</span> addTwoNumbers(l1, l2, <span class="hljs-params">0</span>); } <span class="hljs-keyword">private</span>: <span class="hljs-function">ListNode* <span class="hljs-title">addTwoNumbers</span><span class="hljs-params">(ListNode* l1, ListNode* l2, <span class="hljs-keyword">int</span> carry)</span> </span>{ <span class="hljs-keyword">if</span> (l1 == <span class="hljs-params">nullptr</span> && l2 == <span class="hljs-params">nullptr</span> && carry == <span class="hljs-params">0</span>) <span class="hljs-keyword">return</span> <span class="hljs-params">nullptr</span>; carry += (l1 == <span class="hljs-params">nullptr</span> ? <span class="hljs-params">0</span> : l1->val) + (l2 == <span class="hljs-params">nullptr</span> ? <span class="hljs-params">0</span> : l2->val); <span class="hljs-keyword">auto</span> ret = <span class="hljs-keyword">new</span> ListNode(carry % <span class="hljs-params">10</span>); ret->next = addTwoNumbers(l1 == <span class="hljs-params">nullptr</span> ? l1 : l1->next, l2 == <span class="hljs-params">nullptr</span> ? l2 : l2->next, carry / <span class="hljs-params">10</span>); <span class="hljs-keyword">return</span> ret; } }; <span class="hljs-title">// (類似)尾遞歸</span> <span class="hljs-keyword">class</span> Solution { <span class="hljs-keyword">public</span>: <span class="hljs-function">ListNode* <span class="hljs-title">addTwoNumbers</span><span class="hljs-params">(ListNode* l1, ListNode* l2)</span> </span>{ ListNode* head = <span class="hljs-params">nullptr</span>; addTwoNumbers(head, <span class="hljs-params">nullptr</span>, l1, l2, <span class="hljs-params">0</span>); <span class="hljs-keyword">return</span> head; } <span class="hljs-keyword">private</span>: <span class="hljs-function"><span class="hljs-keyword">void</span> <span class="hljs-title">addTwoNumbers</span><span class="hljs-params">(ListNode*& head, ListNode* cur, ListNode* l1, ListNode* l2, <span class="hljs-keyword">int</span> carry)</span> </span>{ <span class="hljs-keyword">if</span> (l1 == <span class="hljs-params">nullptr</span> && l2 == <span class="hljs-params">nullptr</span> && carry == <span class="hljs-params">0</span>) <span class="hljs-keyword">return</span>; carry += (l1 == <span class="hljs-params">nullptr</span> ? <span class="hljs-params">0</span> : l1->val) + (l2 == <span class="hljs-params">nullptr</span> ? <span class="hljs-params">0</span> : l2->val); <span class="hljs-keyword">auto</span> temp = <span class="hljs-keyword">new</span> ListNode(carry % <span class="hljs-params">10</span>); <span class="hljs-keyword">if</span> (cur == <span class="hljs-params">nullptr</span>) { head = temp; cur = head; } <span class="hljs-keyword">else</span> { cur->next = temp; cur = cur->next; } addTwoNumbers(head, cur, l1 == <span class="hljs-params">nullptr</span> ? l1 : l1->next, l2 == <span class="hljs-params">nullptr</span> ? l2 : l2->next, carry / <span class="hljs-params">10</span>); } }; ``` ``` **復雜度分析** - 時間復雜度:O(N)O(N)O(N) - 空間復雜度:O(N)O(N)O(N),其中 N 的空間是調用棧的開銷。 大家對此有何看法,歡迎給我留言,我有時間都會一一查看回答。更多算法套路可以訪問我的 LeetCode 題解倉庫:<https://github.com/azl397985856/leetcode> 。 目前已經 37K star 啦。 大家也可以關注我的公眾號《力扣加加》帶你啃下算法這塊硬骨頭。 ![](https://img.kancloud.cn/cf/0f/cf0fc0dd21e94b443dd8bca6cc15b34b_900x500.jpg)
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看