Leetcode82. 删除排序链表中的重复元素 II

题目描述

存在一个按升序排列的链表,给你这个链表的头节点 head ,请你删除链表中所有存在数字重复情况的节点,只保留原始链表中 没有重复出现 的数字。

返回同样按升序排列的结果链表。

示例 1:

img

1
2
输入:head = [1,2,3,3,4,4,5]
输出:[1,2,5]

示例 2:

img

1
2
输入:head = [1,1,1,2,3]
输出:[2,3]

提示:

  • 链表中节点数目在范围 [0, 300]
  • -100 <= Node.val <= 100
  • 题目数据保证链表已经按升序排列

解题思路

这道题与Leetcode83. 删除排序链表中的重复元素很类似,但是与之不同的是这道题并不保留数字重复的结点,只是保留原始链表中不重复元素的结点。

所以我们可以直接套用Leetcode83. 删除排序链表中的重复元素中的方法,但是在删除结点的时候做一点改动:将if判断改为while循环,在循环结束的时候删除最后残留的数字重复的结点。删除代码如下示例:

1
2
3
4
5
6
7
8
9
10
if(curPtr->val==curPtr->next->val)
{
while(curPtr&&curPtr->next&&curPtr->val==curPtr->next->val)
{
prePtr->next=curPtr->next;
curPtr=prePtr->next;
}
prePtr->next=curPtr->next;
curPtr=prePtr->next;
}

全部代码如下所示。

示例代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
struct ListNode {
int val;
ListNode *next;
ListNode() : val(0), next(nullptr) {}
ListNode(int x) : val(x), next(nullptr) {}
ListNode(int x, ListNode *next) : val(x), next(next) {}
};

ListNode* deleteDuplicates(ListNode* head)
{
if(head==nullptr||head->next==nullptr) return head;
ListNode* virtualHead=new ListNode(-101,head);
ListNode* prePtr=virtualHead;
ListNode* curPtr=head;

while(curPtr&&curPtr->next)
{
if(curPtr->val==curPtr->next->val)
{
while(curPtr&&curPtr->next&&curPtr->val==curPtr->next->val)
{
prePtr->next=curPtr->next;
curPtr=prePtr->next;
}
prePtr->next=curPtr->next;
curPtr=prePtr->next;
}
else{
prePtr=prePtr->next;
curPtr=curPtr->next;
}
}

return virtualHead->next;
}

时间复杂度为:O(n)O(n)

空间复杂度为:O(1)O(1)