关于LeetCode两数相加LinkedList解法的三点技术疑问
关于LeetCode「两数相加」官方解法的三个疑问解答
先贴出你提到的官方解法代码:
class ListNode: def __init__(self, val=0, next=None): self.val = val self.next = next def addTwoNumbers(l1,l2): dummyHead = ListNode(0) curr = dummyHead carry = 0 while l1 != None or l2 != None or carry != 0: l1Val = l1.val if l1 else 0 l2Val = l2.val if l2 else 0 columnSum = l1Val + l2Val + carry carry = columnSum // 10 newNode = ListNode(columnSum % 10) ##################### curr.next = newNode # curr = newNode # <- Part 1 ############################## l1 = l1.next if l1 else None # <- Part 2 l2 = l2.next if l2 else None # ############################## return dummyHead.next l1 = ListNode(1) l2 = ListNode(2) print(addTwoNumbers(l1=l1,l2=l2).val)
问题1:Part1代码段的逻辑
这两步是链表构建的标准操作,不会丢失next的设置,核心是理解curr是指向链表节点的引用:
- 第一步
curr.next = newNode:此时curr指向当前链表的最后一个节点(第一次循环时是dummyHead),这行代码把该节点的next指针指向新创建的节点,相当于把新节点接到链表末尾。 - 第二步
curr = newNode:把curr这个引用移动到新节点上,确保下一次循环时,能在新节点后面继续添加后续计算的节点,始终让curr指向链表的最后一个节点。
举第一次循环的例子:初始curr指向dummyHead(val=0),执行curr.next = newNode后,dummyHead的next就指向第一个结果节点;然后curr = newNode让curr切换到这个结果节点,下次循环就会给这个节点的next赋值,以此类推构建完整链表。
问题2:Part2代码会不会覆盖原l1内容
不会,这里的l1是函数的局部变量,只是外部传入链表头节点的一个引用副本:
- 执行
l1 = l1.next时,只是改变了这个局部变量的指向,让它从原节点跳转到下一个节点,完全不会修改外部传入的原链表的任何节点内容。 - 外部定义的
l1(比如代码里l1 = ListNode(1)的变量)依然指向原来的节点,不受函数内部赋值操作的影响。
问题3:返回dummyHead.next的逻辑
dummyHead是哨兵节点(dummy node),作用是简化链表的边界处理:
- 初始时dummyHead是一个val=0的占位节点,它本身不属于结果链表。
- 第一次循环时,通过
curr.next = newNode把第一个结果节点接到dummyHead后面,后续所有节点都依次接在这个链表的末尾。 - 最后返回
dummyHead.next,就是跳过占位的dummyHead,直接返回结果链表的头节点,这样就不用单独处理“第一个节点需要特殊赋值”的情况,代码更简洁。
内容的提问来源于stack exchange,提问作者jessefournier
相关产品推荐
相关产品推荐

