删除排序链表的重复元素I和II,多种解法和思考
删除排序链表的重复元素I
https://leetcode.cn/problems/remove-duplicates-from-sorted-list/description/
一个循环就可以了,如果当前节点和下一个节点值一样,当前节点不移动让next后移动一个,如果不一样则当前节点后移。
一个循环就可以了,如果当前节点和下一个节点值一样,当前节点不移动让next后移动一个,如果不一样则当前节点后移。
class Solution {
public ListNode deleteDuplicates(ListNode head) {
if(head==null)
return head;
ListNode cur = head;
while(cur.next!=null){
if(cur.val==cur.next.val)
cur.next=cur.next.next;
else
cur=cur.next;
}
return head;
}
}
删除排序链表的重复元素II
https://leetcode.cn/problems/remove-duplicates-from-sorted-list-ii/description/
学习到的新思想:
1、当不想要某个节点时,可以先找到前置节点然后cur.next=cur.next.next,这样子前面一个节点.next就可以跳过这个节点了,不再需要删除节点再定义两个节点了。为什么不能cur=cur.next;cur的空间始终存在,cur.next只是把空间指向了下一个节点罢了。
PS:当前指针不好改内存,.next指向的改变才是关键所在
2、当某个值得节点都不想要的时候,不要每一次都两个节点进行比较,看是不是两个节点的值一样。可以先开一个变量记录下来节点的值,然后再用1,就可以把所有节点全删了。
class Solution {
public ListNode deleteDuplicates(ListNode head) {
if(head==null) return null;
ListNode dummyNode = new ListNode(0,head);
ListNode cur = dummyNode;
//为什么可以指两次,其实如果不存在.next.next这个节点也不用删掉不是吗
//这样子的变动是在链表head上面进行的
//这里有一步很妙,先拿一个变量记录下来当前节点,然后就可以直接抛弃当前所有
//节点,不要在两个节点进行比较
while(cur.next!=null&&cur.next.next!=null){
int val = cur.next.val;
if(cur.next.val==cur.next.next.val)
while(cur.next!=null&&cur.next.val==val)
cur.next=cur.next.next;
else
cur = cur.next;
}
return dummyNode.next;
}
}
自己的写法,单循环双节点计数法,先得到前面一个节点和当前节点,然后找到计数为1并且前后两个节点值不一样的位置,双节点再移动,又臭又长。
class Solution {
public ListNode deleteDuplicates(ListNode head) {
if(head==null) return null;
//可能会有表头节点全部删除完了的情况,我们依旧采用虚拟节点的写法
ListNode dummyNode = new ListNode(0,head);
ListNode pre = dummyNode;
ListNode cur = dummyNode.next;
//删除节点,让pre指向下一个满足条件的节点即可
int flag = 1;
//计数器flag为1时候就可以赋值了
while(cur.next!=null){
if(cur.val==cur.next.val){
flag++;
cur.next=cur.next.next;
}
else{
if(flag==1){
pre.next=cur;
cur=cur.next;
pre=pre.next;
}
else{
cur=cur.next;
flag=1;
}
}
}
if(flag==1) pre.next=cur;
else pre.next=null;
return dummyNode.next;
}
}
优化了一下过程:
class Solution {
public ListNode deleteDuplicates(ListNode head) {
if(head==null) return null;
ListNode dummyNode = new ListNode(0,head);
ListNode pre = dummyNode;
ListNode cur = head;
while(cur!=null&&cur.next!=null){
if(cur.val==cur.next.val){
int val = cur.val;
while(cur!=null&&cur.val==val)
cur=cur.next;
}
else{
pre.next=cur;
pre=pre.next;
cur=cur.next;
}
}
pre.next=cur;
return dummyNode.next;
}
}