LeetCode ยท #2

Add Two Numbers Solution

Given two non-empty linked lists representing non-negative integers in reverse order, return their sum as a linked list.

01
Section One ยท Problem

Problem Statement

๐Ÿท๏ธ

Difficulty

Medium

๐Ÿ”—

LeetCode

Problem #2

๐Ÿ—๏ธ

Pattern

Math โ€” digit-by-digit with carry

You are given two non-empty linked lists representing two non-negative integers. The digits are stored in reverse order, and each node contains a single digit. Add the two numbers and return the sum as a linked list (also in reverse order).

Example
Input: l1 = 2โ†’4โ†’3 (342) l2 = 5โ†’6โ†’4 (465) Output: 7โ†’0โ†’8 (807) // 342 + 465 = 807
Constraints
โ€ข 1 โ‰ค number of nodes โ‰ค 100 โ€ข 0 โ‰ค Node.val โ‰ค 9 โ€ข No leading zeros (except the number 0 itself)
02
Section Two ยท Approach 1

Convert to Integer โ€” Overflow risk

Convert both lists to integers, add, then convert the result back to a list. Simple but fails for numbers exceeding integer range (up to 100 digits!).

Problem: 100-digit numbers overflow any integer type. The digit-by-digit approach handles arbitrarily long numbers naturally, just like manual addition on paper.
03
Section Three ยท Approach 2

Digit-by-Digit Addition โ€” O(max(m, n))

Add corresponding digits from both lists plus the carry. Store the ones digit in a new node, propagate the tens digit as carry. Continue until both lists and carry are exhausted.

๐Ÿ’ก Mental model: Elementary school long addition. Start from the rightmost digit (which is conveniently the head, since digits are reversed). Add two digits + carry. Write down the ones place, carry the tens place. Move left. This is exactly what we're doing node by node.
Algorithm
  • Step 1: Create a dummy node and a tail pointer. carry = 0.
  • Step 2: While l1 or l2 or carry > 0:
  • Sum = (l1.val or 0) + (l2.val or 0) + carry.
  • carry = sum / 10. digit = sum % 10.
  • Create new node with digit, link it.
  • Advance l1, l2 if not null.
  • Step 3: Return dummy.next.
๐ŸŽฏ Why reverse order helps:
  • Digits are stored least-significant first โ€” exactly the order we need for addition. No reversal required.
  • We start adding from the ones place naturally.
04
Section Four ยท Trace

Visual Walkthrough

Trace: l1 = 2โ†’4โ†’3, l2 = 5โ†’6โ†’4:

Digit-by-digit addition with carry
L1 (342 reversed): 2 โ†’ 4 โ†’ 3 L2 (465 reversed): 5 โ†’ 6 โ†’ 4 ADDITION TRACE (ones โ†’ tens โ†’ hundreds) โ‘  Ones: 2 + 5 + carry(0) = 7 carry = 0 7 7 < 10 โ†’ digit=7, carry stays 0 โ‘ก Tens: 4 + 6 + carry(0) = 10 carry = 1 0 10 โ‰ฅ 10 โ†’ digit=0, carry=1 โ‘ข Hundreds: 3 + 4 + carry(1) = 8 carry = 0 8 Both lists exhausted, carry=0 โ†’ done! RESULT โ†’ โ†’ OUTPUT LIST: 7 โ†’ 0 โ†’ 8 (represents 807 = 342 + 465) 7 โ†’ 0 โ†’ 8 Answer: 7โ†’0โ†’8 (807) โœ“
05
Section Five ยท Implementation

Code โ€” Java & Python

Java โ€” Digit-by-digit
class Solution { public ListNode addTwoNumbers(ListNode l1, ListNode l2) { ListNode dummy = new ListNode(0); ListNode tail = dummy; int carry = 0; while (l1 != null || l2 != null || carry != 0) { int sum = carry; if (l1 != null) { sum += l1.val; l1 = l1.next; } if (l2 != null) { sum += l2.val; l2 = l2.next; } carry = sum / 10; tail.next = new ListNode(sum % 10); tail = tail.next; } return dummy.next; } }
Python โ€” Digit-by-digit
class Solution: def addTwoNumbers(self, l1, l2): dummy = tail = ListNode(0) carry = 0 while l1 or l2 or carry: s = carry if l1: s += l1.val; l1 = l1.next if l2: s += l2.val; l2 = l2.next carry, digit = divmod(s, 10) tail.next = ListNode(digit) tail = tail.next return dummy.next
06
Section Six ยท Analysis

Complexity Analysis

ApproachTimeSpaceTrade-off
Digit-by-digit โ† optimal O(max(m,n)) O(max(m,n)) One pass, handles any length. Space for output list.
07
Section Seven ยท Edge Cases

Edge Cases & Pitfalls

CaseInputWhy It Matters
Different lengths9โ†’9โ†’9 + 9โ†’9Shorter list runs out first โ€” treat missing digits as 0.
Final carry9โ†’9 + 1 = 0โ†’0โ†’1Result is longer than both inputs. The || carry condition handles this.
Zero0 + 00+0+0=0, carry=0 โ†’ single node [0].
โš  Common Mistake: Forgetting to check carry != 0 in the loop condition. If both lists end but carry is 1 (e.g., 99+1=100), you miss the leading 1. Always include carry in the termination condition.

โ† Back to Linked List problems