1)删除
①删头结点
如图:
PDel=head;
head=head->next;
free(PDel);//释放PDel指向的结点,PDel并未删
PDel=NULL;
②删中间结点
如图:
q->next=PDel->next;
free(PDel);
PDel=NULL;
③删尾结点
如图:
q->next=NULL;
free(PDel);
PDel=NULL;
总结:
ⅰ.删头结点,动头指针。
ⅱ.删中间(尾结点),找到带删结点的前驱和后继,将前驱挂在后继上。
例:设head指向一个非空单向链表,其数据域值不重复,在链表中删除关键字key的结点。
ElemSN * DeleteNode(ElemSN *h,int key)
{
ElemSN *p,*q;
for(p=h;p&&p->data-key;q=p,p=p->next);//查找
if(p==h)//删除
h=h->next;
else if(p)
q->next=p->next;
free(p);
p=NULL;
return h;
}
例:设head指向非空单向链表
①设数据域不重复,删除最大值结点/将最大值结点移至链表头(尾)部
②设数据域的值重复,删除关键字值为key的结点。
③设数据域的值重复,且升序有序,删除链表中的重复结点。
④将一个无序链表按降序排列。
①//ⅰ.删除最大值结点
ElemSN * DeleteMax(ElemSN *h)
{
ElemSN *pmax=h,*qmax;
ElemSN *p,*q;
for(p=h;p;q=p,p=p->next)
{
if(p->data > pmax->data)
{
qmax=q;
pmax=p;
}
}
if(pmax==h)
{
h=h->next;
}
else
{
qmax->next=pmax->next;
}
free(pmax);
pmax=NULL;
return h;
}
①//ⅱ.将最大值结点移至链表头
ElemSN * MoveMaxToHead(ElemSN *h)
{
ElemSN *pmax=h,*qmax;
ElemSN *p,*q;
for(p=h;p;q=p,p=p->next)
{
if(p->data > pmax->data)
{
qmax=q;
pmax=p;
}
}
if(pmax-h)
{
qmax->next=pmax->next;
pmax->next=h;
h=pmax;
}
return h;
}
①//ⅲ.将最大值结点移至链表头
ElemSN * DeleteMax(ElemSN *h)
{
ElemSN *pmax=h,*qmax;
ElemSN *p,*q;
for(p=h;p;q=p,p=p->next)
{
if(p->data > pmax->data)
{
qmax=q;
pmax=p;
}
}
if(pmax-q)
{
qmax->next=pmax->next;
q->next=pmax;
pmax->next=NULL;
}
return h;
}
②ElemSN * DeleteRepeatKey(ElemSN *h,int key)
{
ElemSN *p=h,*q;
while(p)
{
if(p->data-key)
{
q=p;
p=p->next;
}
else if(p==h)
{
h=h->next;
free(p);
p=h;
}
else
{
q->next=p->next;
free(p);
p=q->next;
}
}
return h;
}
③ElemSN * DeleteRepeatNode(ElemSN *h)
{
ElemSN *p=h->next,*q=h;
while(p)
{
if(p->data-q->data)
{
q=p;
p=p->next;
}
else
{
q->next=p->next;
free(p);
p=q->next;
}
}
return h;
}
④ElemSN * SortLink(ElemSN *h)
{
ElemSN *hn=NULL,*pmin,*qmin,*p,*q;
for(p=pmin=h;p;p=pmin=h)
{
for(;p;q=p,p=p->next)
{
if(p->data < pmin->data)
{
pmin=p;
qmin=q;
}
}
if(pmin-h)
qmin->next=pmin->next;
else
h=h->next;
pmin->next=hn;
hn=pmin;
}
return hn;
}