链表结点的删除

链表结点的删除

结点的删除分为两种情况:
(1)删除头结点。(需要改变头指针位置)
(2)删除中间,尾结点。(带删除结点的前驱必须有指针,将带删除结点的前驱与带删除结点的后继连起来)

例题1
设head指向一个非空单项链表,且数据域的值不重复,在链表中删除关键字值为key的结点。

分析
第一步:查找值为key的结点(分为能找到和不能找到两种情况)
方法:for(p=h;p&&p->datakey;q=p,p=p->next);
解释:运用空循环,在p指向不为空且p指向的值不为key是循环继续,反之则跳出循环。
第二步:删除该结点
//如果p指向为NULL,则p遍历链表,未找到key值
if(p
NULL)
printf(“未找到。\n”);
//如果p指向不为NULL,则找到了key值
else
{
if(p==head) //删除头结点,注意要返回头指针
else // 删除中间,尾结点
}

具体代码:

#include <iostream>
#include<stdio.h>
#include<stdlib.h>
#define N 10
typedef struct Node
{
    int data;
    struct Node *next;
}Elensn;
//链表的建立
Elensn *initLink(int *a,int n)
{
    int i;
    Elensn *h=NULL,*tail;
    h=tail=(Elensn*)malloc(sizeof(Elensn));
    h->data=a[0];
    h->next=NULL;
    for(i=1;i<n;i++)
    {
        tail=tail->next=(Elensn*)malloc(sizeof(Elensn));
        tail->data=a[i];
        tail->next=NULL;
    }
    return h;
}
//输出链表
void printLink(Elensn* head)
{
    Elensn* p;
    for(p=head;p!=NULL;p=p->next)
        printf("%d\t",p->data);
}

//核心代码,查找并删除key
Elensn* delsinglenode(Elensn* h,int key)
{
    Elensn *p,*q;
    for(p=h;p&&p->data!=key;q=p,p=p->next);//查找待删结点
    if(p==NULL)//如果p跑到了链表末尾
        printf("未找到key。\n");
    else//如果找到了key所在结点
    {
        if(p==h)//如果为头结点
            h=h->next;
        else//如果为中加,尾结点
            q->next=p->next;
        free(p);//释放被删元素key所在结点
        p=NULL;
    }
    return(h);
}
int main()
{
    int a[N]={1,2,3,4,5,6,7,8,9,10},key;
    Elensn * head;
    head=initLink(a,N);
    printf("请输出要删除的内容key\n");
    scanf("%d",&key);
    head=delsinglenode(head,key);
    printLink(head);
    return 0;
}

实现效果
(1)当找到要删除值key值时:
在这里插入图片描述

(2)当未找到要删除值key时:
在这里插入图片描述

例题2
设head指向一个非空单项链表,并且数据域的值不重复,删除链表中的最大值结点

方法一:

#include <iostream>
#include<stdio.h>
#include<stdlib.h>
#define N 10
//数据结构
typedef struct Node
{
    int data;
    struct Node *next;
}Elensn;
//创建链表
Elensn *initLink(int *a,int n)
{
    int i;
    Elensn *h=NULL,*tail;
    h=tail=(Elensn*)malloc(sizeof(Elensn));
    h->data=a[0];
    h->next=NULL;
    for(i=1;i<n;i++)
    {
        tail=tail->next=(Elensn*)malloc(sizeof(Elensn));
        tail->data=a[i];
        tail->next=NULL;
    }
    return h;
}
//链表的输出
void printLink(Elensn* head)
{
    Elensn* p;
    for(p=head;p!=NULL;p=p->next)
        printf("%d\t",p->data);
}
//核心代码,删除最大值结点
Elensn* delmax(Elensn* head)
{
    Elensn *p,*q,*pmax;
    //寻找最大值结点,将pamx指针指向链表中的最大值结点
    for(p=head->next,pmax=head;p;p=p->next)
    //如果p所在结点值大于pmax所指向结点的值,则将pamx指向p所在结点
        if(p->data>pmax->data)
            pmax=p;
     //两指针联动跑,寻找pamx结点所对应的前驱指针q
    for(p=head;p&&p->data!=pmax->data;q=p,p=p->next);
    if(p==head)//如果最大值结点为头结点
        head=head->next;
    else//如果最大值结点为中加,尾结点
        q->next=p->next;
    free(p);//释放最大值结点
    p=NULL;
    return(head);
}
  int main()
{
    int a[N]={15,1,2,3,4,5,6,8,9,7};
    Elensn * head;
    head=initLink(a,N);
    head=delmax(head);
    printLink(head);
    return 0;
}

方法二
相较于第一种方法,第二种方法更为简便,不用再次遍历链表找到pmax的前驱指针,而是在找到pamx指针的同时,寻找它的钱去指针qmax。
核心代码:
Elensn* delmax(Elensn* head)
{
Elensn *p,*q,*pmax=head,*qmax=NULL;
for(q=head,p=head->next;p;q=p,p=p->next)//寻找最大值及pmax,qmax
if(p->data>pmax->data)
{
pmax=p;
qmax=q;
}
if(pmax==head)
head=head->next;
else
qmax->next=pmax->next;
free(pmax);
pmax=NULL;
return(head);
}

实现效果
当数据域中的值为15,1,2,3,4,5,6,8,9,7时,所要删除的最大值为头结点,输出结果为:
在这里插入图片描述

当数据域为1,2,3,4,5,6,8,9,7,15时,所要删除的结点为中加,尾结点时,输出结果为:
在这里插入图片描述

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值