-
[LeetCode] Add Two Numbers코딩테스트/LeetCode 2022. 1. 2. 17:13
문제
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 contains a single digit. Add the two numbers and return the sum as a linked list.
You may assume the two numbers do not contain any leading zero, except the number 0 itself.
두 개의 음이 아닌 정수를 나타내는 비어 있지 않는 linked-list가 주어진다. 숫자는 역순으로 저장되고 각 노드에는 단일 숫자가 포함된다. 두 숫자를 더하고 linked-list로 합을 반환한다. 두 숫자에 숫자 0 자체를 제외하고는 선행 0이 포함되어 있지 않다고 가정한다.
=> 두 linked-list 의 합을 구한다. 각 노드는 단일 숫자(0~9)이기 때문에 다음 노드로 올림 처리를 해줘야 한다.Example
Example 1:
Input: l1 = [2,4,3], l2 = [5,6,4] Output: [7,0,8] Explanation: 342 + 465 = 807.
Example 2:Input: l1 = [0], l2 = [0] Output: [0]
Example 3:Input: l1 = [9,9,9,9,9,9,9], l2 = [9,9,9,9] Output: [8,9,9,9,0,0,0,1]
Constraints:
- The number of nodes in each linked list is in the range [1, 100].
- 0 <= Node.val <= 9
- It is guaranteed that the list represents a number that does not have leading zeros.
풀이
/** * Definition for singly-linked list. * function ListNode(val, next) { * this.val = (val===undefined ? 0 : val) * this.next = (next===undefined ? null : next) * } */ /** * @param {ListNode} l1 * @param {ListNode} l2 * @return {ListNode} */ var addTwoNumbers = function(l1, l2) { const arrayL1 = convertListNodeToArray(l1); const arrayL2 = convertListNodeToArray(l2); const sum = sumArray(arrayL1, arrayL2); return convertArrayToListNode(sum.reverse()); }; function convertListNodeToArray(listNode) { const array = [listNode.val]; while(listNode.next !== null){ listNode = listNode.next; array.push(listNode.val) } return array; } function sumArray(array1, array2) { const newArray = []; const length = array1.length > array2.length ? array1.length : array2.length; let extra = 0; for(let i = 0; i < length; i++) { const value = (array1[i] || 0) + (array2[i] || 0) + extra; extra = Math.floor(value / 10); newArray[i] = value % 10; } if (extra > 0) { newArray[newArray.length] = extra; } return newArray; } function convertArrayToListNode(array) { return array.reduce((acc, curr) => { if (acc == null) { acc = new ListNode(curr); } else { acc = new ListNode(curr, acc); } return acc; }, null); }
=> 생각나는대로 풀었다.
- Runtime: 132ms ~ 231ms
- Memory: 44.2MB ~ 45.5MB
다른 사람 풀이
분포율이 제일 높았던 풀이법
/** * Definition for singly-linked list. * function ListNode(val, next) { * this.val = (val===undefined ? 0 : val) * this.next = (next===undefined ? null : next) * } */ /** * @param {ListNode} l1 * @param {ListNode} l2 * @return {ListNode} */ var addTwoNumbers = function(l1, l2) { const d = new ListNode(); let curr = d; let carry = 0; while (l1 || l2 || carry) { const sum = (l1 ? l1.val : 0) + (l2 ? l2.val : 0) + carry; carry = sum / 10 | 0; curr.next = new ListNode(sum % 10); if (l1) l1 = l1.next; if (l2) l2 = l2.next; curr = curr.next; } return d.next; };
=> 내가 생각했던 로직이였는데, linked-list는 위와 같이 하면 되는 거였다.
Runtime이 가장 빨랐던 풀이법
/** * Definition for singly-linked list. * function ListNode(val, next) { * this.val = (val===undefined ? 0 : val) * this.next = (next===undefined ? null : next) * } */ /** * @param {ListNode} l1 * @param {ListNode} l2 * @return {ListNode} */ var addTwoNumbers = function(l1, l2) { return addNodeList(l1, l2); }; /** * @param {ListNode} l1 * @param {ListNode} l2 * @param {number} extra * @return {ListNode} */ var addNodeList = function(l1, l2, extra = 0) { if (l1 === null && l2 === null && extra === 0) { return null; } var n1 = l1 !== null ? l1.val : 0; var n2 = l2 !== null ? l2.val : 0; var total = n1 + n2 + extra; var digit = total % 10; var newExtra = (total - digit) / 10; var next1 = l1 !== null ? l1.next : null; var next2 = l2 !== null ? l2.next : null; return new ListNode(digit, addNodeList(next1, next2, newExtra)); }
=> 재귀인건가.. 세상에나..
결론
알고리즘 및 코딩테스트 문제를 많이 안 풀어봐서, 기계적으로 Array로 로직을 구현하려고 했다.
linked-list일 경우 로직 처리 방식에 대해 알 수 있었다.
'코딩테스트 > LeetCode' 카테고리의 다른 글
[LeetCode] Palindrome Number (0) 2022.01.04 [LeetCode] Longest Substring Without Repeating Characters (0) 2022.01.03 [LeetCode] Two Sum (0) 2022.01.01