Leetcode题解 - 链表简单部分题目代码+思路(21、83、203、206、24、19、876)
🎃本次部分没有带题目,因为链表系列的题目有的非常直观,从名字中就能知道到底需要做什么。
21. 合并两个有序链表
"""
(用中间链表的方法)可以想象为双指针,分别指向两个链表,比较指针当前指向的值(因为是比较当前的值所以不需要判断next是否为空),拥有较小值的链表指针后移。
"""
class Solution:
def mergeTwoLists(self, l1: ListNode, l2: ListNode) -> ListNode:
head = ListNode(0)
tmp = head
while l1 and l2:
if l1.val <= l2.val:
tmp.next = l1
l1 = l1.next
else:
tmp.next = l2
l2 = l2.next
tmp = tmp.next
if l1:
tmp.next = l1
else:
tmp.next = l2
return head.next
83. 删除排序链表中的重复元素
"""
因为涉及到删除操作,所以需要记录前一个结点的信息
"""
class Solution:
def deleteDuplicates(self, head: ListNode) -> ListNode:
dummy = ListNode(float("inf"))
dummy.next = head
pre = dummy
vis = set()
# pre为当前结点的前一个,head象征当前操作的节点
while pre and head:
if head.val in vis:
# 遇到需要删除的元素,切断当前pre和head的线
pre.next = head.next
head = head.next
continue
vis.add(head.val)
pre = head
head = head.next
return dummy.next
203. 移除链表元素
"""
删除结点,需要记录其前一个结点(和上面一个题目几乎相同)
"""
class Solution:
def removeElements(self, head: ListNode, val: int) -> ListNode:
dummy = ListNode(0)
dummy.next = head
pre = dummy
while pre and head:
if head.val == val:
pre.next = head.next
else:
pre = head
head = head.next
return dummy.next
206. 反转链表
"""
每次遍历到一个结点就插入到新链表的头部(头插法)
"""
class Solution:
def reverseList(self, head: ListNode) -> ListNode:
if not head:
return
newhead = ListNode(head.val)
head = head.next
while head:
tmp = head.next
head.next = newhead
newhead = head
head = tmp
return newhead
24. 两两交换链表中的节点
"""
非常直观(但并算很好的思路),遍历链表,交换奇偶位,重新建立建立链表。
"""
class Solution:
def swapPairs(self, head: ListNode) -> ListNode:
if not head:
return
l = []
while head:
l.append(head.val)
head = head.next
lens = len(l)
if len(l) % 2 != 0:
lens -= 1
for i in range(1, lens, 2):
l[i], l[i-1] = l[i-1], l[i]
thead = ListNode(l.pop(0))
curr = thead
for j in l:
curr.next = ListNode(j)
curr = curr.next
return thead
19. 删除链表的倒数第N个节点
"""
双指针,两个相隔n-1,则快指针走到末尾的时候,慢指针正好走到倒数第n个
"""
class Solution:
def removeNthFromEnd(self, head: ListNode, n: int) -> ListNode:
slow = head
quick = head
# 因为要删除节点,所以需要记录前一个节点
pre = head
# 先让快指针走n-1步
for i in range(n-1):
quick = quick.next
# 如果走完之后已经到了末尾,那么直接删掉头
if not quick.next:
head = head.next
return head
while quick.next:
quick = quick.next
pre = slow
slow = slow.next
pre.next = slow.next
return head
876. 链表的中间结点
"""
遍历链表同时记录位置,直接返回位于中间的结点即可。
"""
class Solution:
def middleNode(self, head: ListNode) -> ListNode:
mat = {}
i = 0
while head:
mat[i] = head
head = head.next
i += 1
return mat[i // 2]