一、前言
最近在刷力扣上的题目,之前也刷过很多次,一边刷一边忘,很是苦恼。
为什么边学边忘,很大程度是没有应用场景,只是被动的进行填鸭式学习。
为了提高学习效率,觉得还是得坚持写博客,一方面强化记忆,第二强迫自己创造应用场景,学习知识的同时也在产生知识。
二、题目
给出两个 非空 的链表用来表示两个非负的整数。其中,它们各自的位数是按照 逆序 的方式存储的,并且它们的每个节点只能存储 一位 数字。
如果,我们将这两个数相加起来,则会返回一个新的链表来表示它们的和。
您可以假设除了数字 0 之外,这两个数都不会以 0 开头。
示例:
输入:(2 -> 4 -> 3) + (5 -> 6 -> 4)
输出:7 -> 0 -> 8
原因:342 + 465 = 807
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/two-sum
三、单链表的相关知识
参考我的其他博文: 【python链表】之单向链表详解
四、学习参考视频
一分钟教你链表反转
视频:一分钟教你链表反转,可以完美解答 算法题206—反转链表
五、解答方法
一、先解决两个链表相加问题,判断中间是否有结果进位。
二、将生成新链表进行链表翻转。
class ListNode:
def __init__(self, x, next=None):
self.val = x
self.next = next # 让next默认为None,方便后期传值。
class Solution:
def addTwoNumbers(self, l1: ListNode, l2: ListNode) -> ListNode:
f = ListNode(0) # 定义输出链表的第一个节点
p = f # p类似于指针,代表输出链表的第一个节点
carry = 0 # 进位
while l1 or l2: # 如果l1或者l2为空,则循环结束
x = l1.val if l1 else 0 # 如果l1不为空则取l1.val否则取0
y = l2.val if l2 else 0
res = x + y + carry # 与进位一起相加的结果
carry = res // 10 # 检查是否有进位
p.next = ListNode(res % 10) # 这个时候p实际是输出链表的第一个节点,它指向下一个节点的地址
p = p.next # 节点进位,这时p指向的是上一行定义的节点
l1 = l1.next if l1 else 0 # 如果l1不为空则取l1.next否则取0
l2 = l2.next if l2 else 0
if carry > 0: # 如果到最后还有进位,那么还要新建个节点记录进位的值
p.next = ListNode(1)
return f.next # 返回的链表一定要从定义的输出链表f的第二个节点开始
if __name__ == '__main__':
a = ListNode(2, ListNode(4, ListNode(3, ))) # 链表a
b = ListNode(5, ListNode(6, ListNode(4, ))) # 链表b
obj = Solution()
Node = obj.addTwoNumbers(a, b)
while Node:
print(Node.val)
Node = Node.next