链表

#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>

typedef struct Link{

    int data;//定义节点的数据
    struct Link *next;//定义指向下一个结点的指针
}L;//定义一个别名为 L 的链表

//表尾插入节点建立链表
L *AppendNode(L *head)
{
    int d;
    L *p1=NULL, *p2=head;//定义两个空指针

    p1 = (L *)malloc(sizeof(L));//为了新建节点申请分配内存空间
    if(p1==NULL)
    {
        printf("ERROR!\n");
        exit(0);
    }//如果内存申请分配失败,则提示错误后退出程序

    else if(head==NULL)
    {
        head = p1;
    }//如果内存申请分配成功并且链表为空表,则置新建节点为头结点

    else
    {
        while(p2->next != NULL)
        {
            p2 = p2->next;
        }//如果指针未到表尾,则直接移动指针直到指针 p2 指向表尾

        p2->next = p1;
    }//如果原链表非空,则将新建节点添加到表尾

    p2 = p1;

    printf("please input data:");
    scanf("%d", &d);
    p2->data = d;
    p2->next = NULL;

    return head;
}

//遍历链表
void DispLink(L *head)
{
    L *p=NULL;

    p = head;//指针指向头结点

    while(p!=NULL)//如果指针指向不为空
    {
        printf("%2d", p->data);//指针指向节点的数据域
        p = p->next;//指针指向节点的指针域
    }

    printf("\n");
}

//释放链表的内存空间
void Delete(L *head)
{
    L *p1=NULL, *p2=NULL;

    p1 = head;
    while(p1!=NULL)
    {
        p2 = p1->next;//指针 p2 指向下一个节点
        free(p1);//释放当前节点的内存
        p1 = p2;//指针 p1 指向下一个节点的指针
    }
}

//删除链表节点
L *DeleteNode(L *head)
{
    int nodedata;
    L *pa = NULL, *pb = NULL;

    //提示输入删除节点的数据
    printf("delete nodedata:");
    scanf("%d", &nodedata);

    pa = head;

    //如果链表为空,则输出错误提示,返回头指针
    if(head==NULL)
    {
        printf("链表为空表!\n");
        return (head);
    }

    //若沒有找到节点,并且未到链表表尾,则继续查找
    while(nodedata != pa->data && pa->next != NULL)
    {
        pb = pa;
        pa = pa->next;
    }

    //如果找到该节点,则删除该节点
    if(nodedata == pa->data)
    {
        if(pa == head){//如果待删除节点为首节点,则改变头结点指针 head 的指向位置
            head = pa->next;
        }
        else {//如果待删除节点不是首节点,则将前一节点的指针指向当前节点的下一个节点
            pb->next = pa->next;
        }
        free(pa);
    }

    //没有找到待删除节点,则提示查找失败
    else
    {
        printf("不存在这个数据节点!\n");
    }


    printf("遍历删除节点后的链表:\n");
    DispLink(head);//遍历链表

    return (head);//返回删除节点的链表头结点指针
}

//在升序链表中插入节点
L *InsertNode(L *head)
{
    int nodedata;
    L *p = NULL, *pa = NULL, *pb = NULL;

    //提示输入插入节点的数据
    printf("insert nodedata:");
    scanf("%d", &nodedata);

    p = (L *)malloc(sizeof(L));

    if(!p)//如果新建节点内存申请失败,则退出程序
    {
        printf("No enough memory!\n");
        exit(0);
    }

    p->data = nodedata;
    p->next = NULL;

    pa = head;

    //如果链表为空,则输出错误提示,返回头指针
    if(head==NULL)
    {
        printf("链表为空表!无法插入节点\n");
        return (head);
    }


    else//若链表非空
    {
        while(nodedata > pa->data && pa->next != NULL)//若沒有找到节点,并且未到链表表尾,则继续查找
        {
            pb = pa;
            pa = pa->next;
        }

        //如果找到该节点插入位置,则插入该节点
        if(nodedata < pa->data)
        {
            if(pa == head){//在首节点插入新建节点
                head = p;
                p->next = pa;
            }
            else {//如果待插入节点不是首节点,则将前一节点的指针指向当前节点
                p->next = pb->next;
                pb->next = p;
            }
        }
        else//如果未找到该节点插入位置,且新建节点数据值比链表中的所有数据值大,则把新插入的节点插到表尾
        {
            pa->next = p;
            p->next = NULL;
        }
    }

    printf("遍历插入新节点后的链表:\n");
    DispLink(head);//遍历链表

    return (head);//返回删除节点的链表头结点指针
}

//主函数,驱动测试
void main()
{
    L *head = NULL;
    int i = 0, n = 5;
    int nodedata_1, nodedata_2;//分别定义一个插入节点,一个删除节点

    for(i=0; i<n; i++)
    {
        head = AppendNode(head);
    }

    //遍历链表
    printf("遍历原始链表:\n");
    DispLink(head);

    //删除链表节点
    DeleteNode(head);

    //插入链表节点
    InsertNode(head);

    //释放链表的内存空间
    Delete(head);
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值