快慢指针指的是两个一前一后的指针,两个指针往同一个方向走,只是一个快一个慢。快慢指针严格来说只能有俩,不过实际做题中,可能会出现一前、一中、一后的三个指针,这种超过两个指针的解题方法也叫“多指针法”。快慢指针+多指针,双管齐下,可以帮助我们解决链表中的大部分复杂操作问题。
dummy 结点:它可以帮我们处理掉头结点为空的边界问题,帮助我们简化解题过程。因此涉及链表操作、尤其是涉及结点删除的题目(对前驱结点的存在性要求比较高),我都建议大家写代码的时候直接把 dummy 给用起来,建立好的编程习惯:
const dummy = new ListNode()
// 这里的 head 是链表原有的第一个结点
dummy.next = head
思路
- 首先两个指针
slow
和fast
,全部指向链表的起始位——dummy
结点: - 快指针先出发!闷头走上
n
步,在第n
个结点处打住,这里n=2
: - 然后,快慢指针一起前进,当快指针前进到最后一个结点处时,两个指针再一起停下来
此时,慢指针所指的位置,就是倒数第
n
个结点的前一个结点。基于此节点进行删除 ```javascript /**- @param {ListNode} head
- @param {number} n
@return {ListNode} */ const removeNthFromEnd = function(head, n) { // 初始化 dummy 结点 const dummy = new ListNode() // dummy指向头结点 dummy.next = head // 初始化快慢指针,均指向dummy let fast = dummy let slow = dummy
// 快指针闷头走 n 步 while(n!==0){
fast = fast.next
n--
}
// 快慢指针一起走 while(fast.next){
fast = fast.next slow = slow.next
}
// 慢指针删除自己的后继结点 slow.next = slow.next.next // 返回头结点 return dummy.next };
```