leetcode刷题记--> 19题解法(python解析)
题目定义
给定一个链表,删除链表的倒数第 n 个节点,并且返回链表的头结点。
示例:
给定一个链表: 1->2->3->4->5, 和 n = 2.
当删除了倒数第二个节点后,链表变为 1->2->3->5.
说明:
给定的 n 保证是有效的。
进阶:
你能尝试使用一趟扫描实现吗?
来源:力扣(LeetCode)
链接: leetcode_19题.
解题
本次使用4种方法,在leetcode上还有更多的方法,只能说真牛逼,真聪明。
1. 转为列表,然后再转为链表
先将链表转为列表,然后将列表转换为链表
2. 使用递归的思路
需要自己debug来进行理解
3. 使用字典存储的方法
首先将链表分为不同的节点进行存储,然后一步步的将链表进行替换
4. 使用单指针
定义单指针
先计算出链表的长度
然后通过链表长度减去n 就是要铲除的那个节点的前一个节点
然后循环
5. 使用双指针
定义双指针
先让first指针先走 先走n步
然后再让first和second同时走 当first走到末尾的时候 second也就走到要删除的那个节点的前一个节点 其实就是两者的一个差值
===================================================
实现
// An highlighted block
# Definition for singly-linked list.
class ListNode:
def __init__(self, x):
self.val = x
self.next = None
class Solution:
def removeNthFromEnd(self, head, n):
'''
就是将链表转为列表 然后通过列表将需要删的值删掉 然后再把列表转为链表(此处需要注意浅拷贝和深拷贝)
'''
# 边界值
if not head or n <= 0:
return None
# 转成列表
l = []
while head:
l.append(head.val)
head = head.next
# 防越界
if n > len(l):
return None
# 使用pop()移除倒数第n个数后,转为链表
l.pop(-n)
new_head = ListNode(0)
p = new_head # 注意此处为浅拷贝 p变了 new_head 也会变 #相当于是一个指针
for j in l:
p.next = ListNode(j)
p = p.next
# 打印出结果
# while new_head:
# print(new_head.val)
# new_head = new_head.next
return new_head.next
def removeNthFromEnd_1(self, head, n):
'''
递归
'''
def removeNode(node, n) :
if node.next == None:
return 1
m = removeNode(node.next, n)
if m == n:
if m == 1:
node.next = None
else:
node.next = node.next.next
return m + 1
return head.next if removeNode(head,n)==n else head
def removeNthFromEnd_2(self, head, n):
'''
使用字典
'''
dummy = ListNode(0)
dummy.next = head
hash_key = {}
head2 = dummy
i=0
while head2.next!=None:
hash_key[i]=head2
head2 = head2.next
i+=1
hash_key[i]=head2
hash_key[i - n ].next = hash_key.get(i-n+2)
return dummy.next
def removeNthFromEnd_3(self, head, n):
'''
定义单指针
先计算出链表的长度
然后通过链表长度减去n 就是要铲除的那个节点的前一个节点
然后循环
'''
dummy = ListNode(0)
dummy.next=head
length = 0
first = head
# 找见链表有多长
while first:
length+=1
first = first.next
length-=n
first = dummy # 重新给first赋值
while length>0:
length-=1 # 2 1
first=first.next
first.next = first.next.next
return dummy.next
def removeNthFromEnd_4(self, head, n):
'''
定义双指针
先让first指针先走 先走n步
然后再让first和second同时走 当first走到末尾的时候 second也就走到要删除的那个节点的前一个节点 其实就是两者的一个差值
'''
dummy = ListNode(0)
dummy.next = head
first = dummy
second = dummy
# 先让first 走n 步
for i in range(0,n+1):
first = first.next
while first: # second和first同时往前走 当first走到头时,second即是要删除节点的前一个节点位置
first = first.next
second = second.next
second.next = second.next.next
return dummy.next
def print_node(self,node):
while node:
print(node.val)
node = node.next
a = ListNode(1)
b = ListNode(2)
c = ListNode(3)
d = ListNode(4)
e = ListNode(5)
f = ListNode(6)
a.next = b
b.next = c
c.next = d
d.next = e
e.next = f
s = Solution()
node = s.removeNthFromEnd_1(a,2)
s.print_node(node)
来源:CSDN
作者:康泽的学习之路
链接:https://blog.csdn.net/qq_42274068/article/details/104037210