Offer 驾到,掘友接招!我正在参与2022春招打卡活动,点击查看活动详情。
一、题目描述:
题目来源:LeetCode-移除重复节点
编写代码,移除未排序链表中的重复节点。保留最开始出现的节点。
示例1:
输入:[1, 2, 3, 3, 2, 1]
输出:[1, 2, 3]
示例2:
输入:[1, 1, 1, 1, 2]
输出:[1, 2]
提示:
链表长度在[0, 20000]范围内。
链表元素在[0, 20000]范围内。
进阶:
如果不得使用临时缓冲区,该怎么解决?
二、思路分析:
思路一:
- 对链表进行遍历,使用HashSet存储所有出现过的元素
- 因为HashSet的特性,不会存在重复的元素,所以在遍历链表进行添加时,自动会过滤掉重复的元素
- 遍历完成后,对、HashSet所有的元素进行输出即可
思路二:
- 使用双层循环
- 第一层循环从链表的头节点开始,列一个保留的节点
- 第二层循环从保留的节点开始,到链表的结尾,将所有与保留节点相同的元素删除
三、AC 代码:
思路一:
class Solution {
public ListNode removeDuplicateNodes(ListNode head) {
if (head == null) {
return head;
}
Set<Integer> set = new HashSet<Integer>();
set.add(head.val);
ListNode positionNode = head;
while (positionNode.next != null) {
ListNode cur = positionNode.next;
if (set.add(cur.val)) {
positionNode = positionNode.next;
} else {
positionNode.next = positionNode.next.next;
}
}
positionNode.next = null;
return head;
}
}
思路二:
class Solution {
public ListNode removeDuplicateNodes(ListNode head) {
ListNode obtainNode = head;
while (obtainNode != null) {
ListNode oc = obtainNode;
while (oc.next != null) {
if (oc.next.val == obtainNode.val) {
oc.next = oc.next.next;
} else {
oc = oc.next;
}
}
obtainNode = obtainNode.next;
}
return head;
}
}
四、总结:
这道题中,我们需要移除未排序链表中的重复节点。保留最开始出现的节点。在一些例如C++的语言中,并没有较好的内存回收机制,因此如果在面试中遇到了本题,可以和面试官确认是否需要释放被移除的节点占用的内存空间。