445 Add Two Numbers II
You are given two non-empty linked lists representing two non-negative integers. The most significant digit comes first 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.
Follow up: What if you cannot modify the input lists? In other words, reversing the lists is not allowed.
Example:
Input: (7 -> 2 -> 4 -> 3) + (5 -> 6 -> 4)
Output: 7 -> 8 -> 0 -> 7The Idea: Reverse both lists. Then set them to be equal in size by appending 0s to the smaller list. Then sum both lists element by element by using a carry. Create this list along the way. Finally, append the carry at the end assuming it is not zero.
Complexity: O(N) time and space, both of which have heavy constants (would not recommend this implementation).
pair<int, ListNode*> reverse_list(ListNode *&l) {
ListNode *iter_front = l, *iter_back = l, *prev_back = nullptr;
stack<ListNode*> s_rev;
int size = 0;
while (iter_back) {
s_rev.push(iter_back);
prev_back = iter_back;
iter_back = iter_back->next;
size++;
}
int swap_half = s_rev.size() / 2;
while (swap_half) {
swap(iter_front->val, s_rev.top()->val);
--swap_half; s_rev.pop();
iter_front = iter_front->next;
}
return {size, prev_back };
}
void make_same_size(pair<int, ListNode*> size_end1, pair<int, ListNode*> size_end2) {
int diff = size_end1.first - size_end2.first;
while (diff > 0) {
ListNode *node = new ListNode(0);
size_end2.second->next = node;
size_end2.second = node;
--diff;
}
while (diff < 0) {
ListNode *node = new ListNode(0);
size_end1.second->next = node;
size_end1.second = node;
++diff;
}
assert(diff == 0);
}
ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {
pair<int, ListNode*> l1_s = reverse_list(l1);
pair<int, ListNode*> l2_s = reverse_list(l2);
make_same_size(l1_s, l2_s);
ListNode *head = nullptr;
ListNode *iter = head;
int carry = 0;
while (l1) { // both are equal in size
int i_s1 = l1->val; l1 = l1->next;
int i_s2 = l2->val; l2 = l2->next;
int sum = i_s1 + i_s2 + carry;
int digit = sum % 10;
carry = sum / 10;
if (head) {
ListNode *node = new ListNode(digit);
iter->next = node;
iter = node;
}
else {
head = new ListNode(digit);
iter = head;
}
}
if (carry) {
ListNode *node = new ListNode(carry);
if (head)
iter->next = node;
else head = node;
}
reverse_list(head);
return head;
}Testing
Simplified Python Implementation:
Convert to stack. Add the stacks together as you pop. Maintain a carry. Add the remainder of a an unfinished stack. Rebuild the linked list from the answer stack.
Last updated
Was this helpful?