Idiot-maker

  :: 首页 :: 博问 :: 闪存 :: 新随笔 :: 联系 :: 订阅 订阅 :: 管理 ::

https://oj.leetcode.com/problems/remove-duplicates-from-sorted-list-ii/

Given a sorted linked list, delete all nodes that have duplicate numbers, leaving only distinct numbers from the original list.

For example,
Given 1->2->3->3->4->4->5, return 1->2->5.
Given 1->1->1->2->3, return 2->3.

解题思路:

这道题与前面的Remove Duplicates from Sorted List相似,却采用了不同的思路。Remove Duplicates from Sorted List 是当前节点与前面的值比较,如果比前面的大,就加入。而本题是,当前节点与后面节点相比,如果后面节点比当前节点大,而且当前节点比再前一个值小,就加入。代码如下。

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) {
 *         val = x;
 *         next = null;
 *     }
 * }
 */
public class Solution {
    public ListNode deleteDuplicates(ListNode head) {
        if(head == null){
            return null;
        }
        
        ListNode dummyNode = new ListNode(head.val - 1);
        dummyNode.next = head;
        ListNode preNode = dummyNode;
        ListNode currentNode = head;
        ListNode nextNode = head.next;
        ListNode keepNode = preNode;

        while(nextNode != null){
            if(preNode.val < currentNode.val && currentNode.val < nextNode.val){
                keepNode.next = currentNode;
                keepNode = keepNode.next;
            }
            preNode = preNode.next;
            currentNode = currentNode.next;
            nextNode = nextNode.next;
        }
        
        //循环结束,这时preNode为倒数第二个节点,currentNode为最后一个节点
        if(preNode.val < currentNode.val){
            keepNode.next = currentNode;
            keepNode = keepNode.next;
        }
        keepNode.next = null;
        return dummyNode.next;
    }
}

这道题的关键在于要时刻保留三个指针,只有中间那个的值大于前面的并且小于后面的,才能加入中间那个节点。还需要注意最后一轮,preNode为倒数第二个节点,currentNode为最后一个节点的时候,要再加一次判断。最后,一定要注意,把keepNode.next置为null,否则遇到1-1这样的要出错。

下面的代码是另一种实现,思路略微不同,但是代码要复杂很多。当前节点与后面节点相比,如果后面节点比当前节点大,就要把当前节点加入。如果相等的话,把当前值作为重复值(invalidValue),这样在判断1-3-3-4-4这样情况的的第二个3时,虽然后面的4大于当前的3,但是3==invalidValue,所以3不能加入。

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) {
 *         val = x;
 *         next = null;
 *     }
 * }
 */
public class Solution {
    public ListNode deleteDuplicates(ListNode head) {
        if(head == null){
            return null;
        }
        
        ListNode dummyNode = new ListNode(head.val - 1);
        dummyNode.next = head;
        ListNode keepNode = dummyNode;
        ListNode traverseNode = dummyNode.next;
        int invalidVal = dummyNode.val;
        
        while(traverseNode != null){
            //如果traverseNode的后一个节点为空
            if(traverseNode.next == null){
                //看看traverseNode本身是不是重复的节点,不是就加入
                 if(traverseNode.val != invalidVal){
                    keepNode.next = traverseNode;
                    keepNode = keepNode.next;
                    traverseNode = traverseNode.next;
                 }else{
                     traverseNode = traverseNode.next;
                 }
            }else{
                //traverseNode的后一个节点大于它,就把它加入,还要注意1-3-3-4-4,traverseNode在第二个3的情况
                //所以要加入一个invalidVal记录当前的重复值,不能加入
                if(traverseNode.next.val > traverseNode.val && traverseNode.val != invalidVal){
                    keepNode.next = traverseNode;
                    keepNode = keepNode.next;
                    traverseNode = traverseNode.next;
                }else{//如果traverseNode的后一个节点等于它
                    invalidVal = traverseNode.val;
                    traverseNode = traverseNode.next;
                }
            }
        }
        keepNode.next = null;
        return dummyNode.next;
    }
}

update 2015/05/19:

二刷

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) { val = x; }
 * }
 */
public class Solution {
    public ListNode deleteDuplicates(ListNode head) {
        if(head == null || head.next == null) {
            return head;
        }
        ListNode dummy = new ListNode(0);
        int pre = head.val - 1;
        ListNode cur = head;
        ListNode slow = dummy;
        while(cur != null) {
            if(cur.val != pre && (cur.next == null || cur.val != cur.next.val)) {
                slow.next = cur;
                slow = slow.next;
            } else {
                slow.next = null;
            }
            pre = cur.val;
            cur = cur.next;
        }
        return dummy.next;
    }
}

 // 20180806

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) { val = x; }
 * }
 */
class Solution {
    public ListNode deleteDuplicates(ListNode head) {
        if (head == null || head.next == null) {
            return head;
        }
        
        ListNode dummy = new ListNode(head.val - 1);
        dummy.next = head;
        ListNode pre = dummy;
        ListNode next = dummy.next;
        while (next != null && next.next != null) {
            if (next.val == next.next.val) {
                while (next.next != null && next.val == next.next.val) {
                    next = next.next;
                }
                pre.next = next.next;
                next = next.next;
            } else {
                pre = pre.next;
                next = next.next;
            }
        }
        return dummy.next;
    }
}

 

posted on 2015-03-03 19:38  NickyYe  阅读(179)  评论(0编辑  收藏  举报