题目

Remove Nth Node From End of List

Given a linked list, remove the nth node from the end of list and return its head.

For example,

Given linked list: 1->2->3->4->5, and n = 2.

After removing the second node from the end, the linked list becomes 1->2->3->5.

Note:
Given n will always be valid.
Try to do this in one pass.

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) { val = x; }
 * }
 */
public class Solution {
    public ListNode removeNthFromEnd(ListNode head, int n) {
    }
}

leetcode链接

https://leetcode.com/problems...

算法

由于题目要求尽量只遍历一遍,所以我们也只考虑只遍历一遍的方法。为了解决问题,我们需要定义两个指针,left和right,left的初始值为我们所创建的ListNode,它的下一个节点为head,right一开始所指向的位置为left之后的第n个节点,也就是说一开始的时候,left和right之间有n - 1个节点,以题目中的单链表和n为例,left,head和right的初始位置如图所示。

ListNode-> 1 -> 2 -> 3 -> 4 -> 5
    ^      ^    ^
    |      |    |
    |      |    |
   left   head right

然后将left和right逐步向右移动,一直到right的下一个节点为null为止,移动的过程如下。

ListNode -> 1 -> 2 -> 3 -> 4 -> 5
            ^         ^
            |         |
            |         |
        left/head   right

ListNode -> 1 -> 2 -> 3 -> 4 -> 5
            ^    ^         ^
            |    |         |
            |    |         |
           head left     right

ListNode -> 1 -> 2 -> 3 -> 4 -> 5
            ^         ^         ^
            |         |         |
            |         |         |
           head      left     right

当我们移动到上图所示的情形(rigth.next == null)时,我们只需要把left的下一个节点去除即可,代码如下:

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) { val = x; }
 * }
 */
public class Solution {
    public ListNode removeNthFromEnd(ListNode head, int n) {

        // pinpoint the initial point of the left pointer and the right pointer
        ListNode left = new ListNode(0);
        left.next = head;
        ListNode right = head;
        int i = 1;
        while(i++ != n) right = right.next;

        // move the left pointer and the right pointer simultaneously until we
        // hit the end of the list
        while(right.next != null) {
            left = left.next;
            right = right.next;
        }

        if(left.next == head) {
            return head.next;
        } else {
            // remove the Node where left.next points
            left.next = left.next.next;
        }
        return head;
    }
}

这种算法的时间复杂度为O(n),空间复杂度为O(1)。


searene
1 声望0 粉丝