【鏈表】C013_LC_移除重複節點(hash 表 / 雙指針)

一、Problem

編寫代碼,移除未排序鏈表中的重複節點。保留最開始出現的節點。

示例1:
 輸入:[1, 2, 3, 3, 2, 1]
 輸出:[1, 2, 3]
 
示例2:
 輸入:[1, 1, 1, 1, 2]
 輸出:[1, 2]

提示:
鏈表長度在[0, 20000]範圍內。
鏈表元素在[0, 20000]範圍內。

進階:

如果不得使用臨時緩衝區,該怎麼解決?

二、Solution

方法一:超級暴力

class Solution {
    public ListNode removeDuplicateNodes(ListNode head) {
        if (head == null)
            return null;
    	Set<Integer> st = new HashSet<>();
    	List<Integer> nums = new ArrayList<>();
    	ListNode h = head;
    	while (h != null) {
            if (!st.contains(h.val)) {
    			st.add(h.val);
    			nums.add(h.val);
    		}
    		h = h.next;
    	}

    	ListNode dead = new ListNode(-1), hh = new ListNode(nums.get(0));
    	dead.next = hh;

    	for (int i = 1; i < nums.size(); i++) {
    		ListNode t = new ListNode(nums.get(i));
    		hh.next = t;
            hh = hh.next;
    	}
    	return dead.next;
    }
}

其實我們只需要修改指針的引用,這樣可以省去 nums 列表

class Solution {
    public ListNode removeDuplicateNodes(ListNode head) {
        if (head == null)
            return null;
    	Set<Integer> st = new HashSet<>();
    	ListNode h = head;

    	while (h != null && h.next != null) {
            st.add(h.val);
            if (!st.contains(h.next.val)) {
    			h = h.next;
    		} else {
            	h.next = h.next.next;
    		}
    	}
    	return head;
    }
}

複雜度分析

  • 時間複雜度:O(n)O(n)
  • 空間複雜度:O(n)O(n)

方法二:時間換空間

不用 hash 表的話,我們就不能快速地某個點的後繼結點知道是否是重複元素了,所以這需要再開一重循環來檢查某個點 ii 的後續結點中第一個不重複元素位置 jj,然後將 i.next = j 實現刪除

...

複雜度分析

  • 時間複雜度:O(n2)O(n^2)
  • 空間複雜度:O(1)O(1)
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章