现在有一个单链表。链表中每个节点保存一个整数,再给定一个值val,把所有等于val的节点删掉。
给定一个单链表的头结点head,同时给定一个值val,请返回清除后的链表的头结点,保证链表中有不等于该值的其它值。请保证其他元素的相对顺序。
ListNode* clear(ListNode* head, int val) {
if(!head)
return nullptr;
while(head->val==val){ //注意了,不是if而是while因为新的头部也可能是待删的。
//所以可见头结点链表的优越性
ListNode* t=head->next;
delete head;
head=t;
}
if(!head)
return nullptr;
ListNode* p=head; //
while(p->next){
if(p->next->val==val){
ListNode* t=p->next;
p->next=t->next;
delete t;
}
else //加上else
p=p->next; //注意不能所有情况都next,这样两个连在一起的就会出错。
}
return head;
}
思考
看似很简单的问题,其实很容易出错:
- 首结点就是待删结点的问题:
以为做一个简单的if就可以了,实际上不是,因为删掉首结点,露出来的新首结点可能还是待删结点。所以要做一个循环来得到第一个非删结点。此时可以看到,带头结点的链表处理起来会顺利多得多。 - 遍历指针的问题:
如果删除了某个结点,遍历指针直接跳到该结点后?还是结点前?一不小心就会少删,对于相同值连在一起的情况