携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第1天,点击查看活动详情
有人相爱,有人夜里开车看海,我却leetcode第二题都做不出来...
题目描述
原题链接:2.两数相加
给你两个
非空的链表,表示两个非负的整数。它们每位数字都是按照逆序的方式存储的,并且每个节点只能存储一位数字。 请你将两个数相加,并以相同形式返回一个表示和的链表。 你可以假设除了数字0之外,这两个数都不会以0开头。
/ 测试用例一 /
输入: l1 = [2,4,3], l2 = [5,6,4]
输出: [7,0,8]
解释: 342 + 465 = 807
-----------------------------------
/ 测试用例二 /
输入: l1 = [0], l2 = [0]
输出: [0]
-----------------------------------
/ 测试用例三 /
输入: l1 = [9,9,9,9,9,9,9], l2 = [9,9,9,9]
输出: [8,9,9,9,0,0,0,1]
思路
链表是用next指针连在一起的元素列表,JavaScript中没有链表,我们可以用Object模拟链表
//创建链表的构造函数
function ListNode(val, next) {
this.val = val ?? 0
this.next = next ?? null
}
- 首先肯定是新建一个虚拟的节点,然后把入参
l1、l2两个链表同位val之和放入虚拟节点的后面 - 判断每次的和有溢出的话,就存进一个自由变量,留给下一位相加
- 下一次
l1、l2链表同位val之和相加要把上一次的进位结算进去 - 思维发散,递归、循环都写一遍
Code
/**
* @param {ListNode} l1
* @param {ListNode} l2
* @return {ListNode}
*/
/** 循环版 */
const addTwoNumbers1 = (l1, l2)=>{
//创建一个新链表
const node = new ListNode()
//创建当前链表节点变量、进位值变量、同位之和变量
let current = node, add = 0, sum = 0;
//当且仅当l1和l2的节点数值都为null才结束循环
while (l1 || l2) {
sum = (l1 ? l1.val : 0) + (l2 ? l2.val : 0) + add
current.next = new ListNode(sum % 10) //当链表同位之和超过10 就取溢出值
current = current.next
add = sum >= 10 ? 1 : 0
l1 && (l1 = l1.next)
l2 && (l2 = l2.next)
}
add && (current.next = new ListNode(add))
return node.next
};
/** 递归版 */
const addTwoNumbers2 = (l1,l2)=> dfs(l1, l2, 0)
const dfs=(l1,l2,add)=>{
//如果l1,l2为空,进位数为0,递归结束
if (!l1 && !l2 && add === 0) {
return null
}
const sum = (l1 ? l1.val : 0) + (l2 ? l2.val : 0) + add
const node = new ListNode(sum % 10)
node.next = dfs(l1 ? l1.next : null, l2 ? l2.next : null, Math.floor(sum / 10));
return node
}
复杂度分析
- 时间复杂度:
O(max(m,n))n取最长链表的长度 - 空间复杂度:循环版
O(1);递归版O(max(m,n))