【路飞】leetcode-19. 删除链表的倒数第 N 个结点

140 阅读1分钟

加油 第 9 练 2022第一练 新的一年 ヾ(◍°∇°◍)ノ゙

19. 删除链表的倒数第 N 个结点

题目描述:给你一个链表,删除链表的倒数第 n 个结点,并且返回链表的头结点。

方法一:两次循环
  • 第一遍循环获取链表的长度L,第二遍循环在指定位置删除节点
  • 倒数第n个节点,即正数第L-n+1个节点
var removeNthFromEnd = function (head, n) {
    // 两次循环,第一次获得长度,第二次移除指定节点
    let dummy = new ListNode(0);
    dummy.next = head;

    let l = 0, temp = dummy;
    while (temp.next) {
        l++;
        temp = temp.next;
    }
    temp = dummy;
    // 倒数第n个节点,正数第l-n+1个节点
    let removeNode = l - n + 1;
    for (let i = 1; i < removeNode; i++) {
        temp = temp.next;
    }
    // 第l-n+1个节点即为要删除的节点
    temp.next = temp.next.next
    return dummy.next;
};
方法二:数组
  • 将链表存入数组,数组倒数第n个的前一个节点与后一个节点相连
var removeNthFromEnd = function(head, n) {
    let dummy = new ListNode(0);
    dummy.next = head;
    let newArr = [],temp = dummy
    while(temp){
        newArr.push(temp)
        temp = temp.next
    }
    //newArr[newArr.length - n - 1].next =  newArr[newArr.length - n + 1]
    // 这样可能会有数组取值 undefined 情况
    newArr[newArr.length - n - 1].next =  newArr[newArr.length - n - 1].next.next
    
    return dummy.next;
};
  • 栈 :链表存入数组,暴露出链表倒数第n个的前一个节点,将其与第n个的后一个节点相连、
var removeNthFromEnd = function(head, n) {
    let dummy = new ListNode(0);
    dummy.next = head;
    let newArr = [],temp = dummy
    while(temp){
        newArr.push(temp)
        temp = temp.next
    }
    for(let i = 0; i < n; i++){
        newArr.pop()
    }
    newArr[newArr.length - 1].next = newArr[newArr.length - 1].next.next
    return dummy.next;
};
方法三:双指针
  • 快指针比慢指针超前n个节点,双指针同时移动,这样当快指针遍历到链表的末尾时,慢指针刚好处于倒数第n个节点
var removeNthFromEnd = function(head, n) {
    let dummy = new ListNode(0);
    dummy.next = head;
    
    let fast = dummy,slow = dummy,i = 0;
    while(i < n){
        fast = fast.next
        i++;
    }
    while(fast.next){
        slow = slow.next
        fast = fast.next
    }
    // 遍历后得到的为倒数第n个节点的前节点
    slow.next = slow.next.next;
    return dummy.next;
};