在一个排序的链表中,删除重复的节点,重复的节点不保留
思路:假设有一个线段,把不重复的节点全部放到这个线段里面,重复的就直接跨过。
代码示例:
public void removeall() {
Nodee bs = null;//让be和bs来创建一条线段,用来装不重复的数字。
Nodee be = null;//让be走,bs在第一个cur处。
Nodee cur = this.head;//让cur来遍历单链表
while (cur != null) {//当cur为null的时候就是这个单链表里面所有的节点都被判断完的时候
if (cur.next != null && cur.data == cur.next.data) {//cur走到最后一个节点的时候,当最后一个节点不重复的时候,cur.next=null,判断cur.next.data会空指针异常
while (cur.next != null && cur.data == cur.next.data) {//万一中间有很多重复的数字,所以需要加上一个循环让cur一直往后走。同样也是为了防止cur走到最后一个的时候,如果还是和前面相等的话,还需要继续判断cur.data和cur.next.data,此时又会空指针异常。
cur = cur.next;
}//这个循环结束的时候,cur走到了最后一个重复数字。
cur = cur.next;//还需要让cur再往后走一步,不然的话最后一个重复数字会进入else,被插入到线段中。如果最后一个数字还是重复的话,cur此时已经为null了。不重复的话。进入else,执行完后cur也变为null了。
} else {
if (bs == null) {
bs = cur;
be = cur;
} else {
be.next = cur;
be = cur;
}
cur = cur.next;
}
}
this.head = bs;
be.next = null;
}
总结:定义两个引用类型的变量bs和be,初始化为null,再定义一个cur从头开始遍历单链表,判断cur.data和cur.next.data的关系。当遇到重复的节点就进入循环,让cur=cur.next,直到cur.data不再等于cur.next.data为止。这个循环退出的时候cur来到了最后一个重复节点的位置,此时还需要再让cur走一步,走到最后一个不重复节点的后面一个节点处。当第一次遇到不重复的节点的时候,让be和bs都等于cur。然后后面又遇到的时候让be.next=cur,再让be=cur。当所有的节点判断完的时候新的头节点也就是bs,新的尾节点也就是be。此时把be.next置为null。
特殊情况:
当cur来到了最后一个节点且最后一个节点也是重复的时候,此时判断循环条件:cur.datacur.next.data,此时会空指针异常。
当cur来到最后一个节点的时候且最后一个节点不重复的时候,cur此时不为null,继续进入循环,此时判断cur.nextcur.next.data的时候也会空指针异常