P4 链表的节点数统计与链表数据查找替换

目录

前言  

01 链表的节点数统计

02 链表数据查找替换 

2.1 残疾的数据查找

2.2 数据查找优化


前言  

                                

🎬 个人主页:@ChenPi

🐻推荐专栏1: 《C++ 》✨✨✨ 

🔥 推荐专栏2: 《 Linux C应用编程(概念类)》✨✨✨

📝推荐专栏3: ​​​​​​《链表_@ChenPi的博客-CSDN博客》 ✨✨✨
🍉本篇简介  :  使用代码的形式演示链表与数组的区别

✨ 只有我努力了 才有机会接触成功✨

链表是一种常见的基础数据结构,结构体指针在这里得到了充分的利用。链表可以动态的进行存储分配,也就是说,链表是一个功能极为强大的数组,他可以在节点中定义多种数据类型,还可以根据需要随意增添,删除,插入节点。链表都有一个头指针,一般以head来表示,存放的是一个地址。链表中的节点分为两类,头结点和一般节点,头结点是没有数据域的。链表中每个节点都分为两部分,一个数据域,一个是指针域。说到这里你应该就明白了,链表就如同车链子一样,head指向第一个元素:第一个元素又指向第二个元素;……,直到最后一个元素,该元素不再指向其它元素,它称为“表尾”,它的地址部分放一个“NULL”(表示“空地址”),链表到此结束。

作为有强大功能的链表,对他的操作当然有许多,比如:

  1. 链表的创建
  2. 链表的链表的遍历打印数据
  3. 链表里面的结构体数据的修改
  4. 链表节点的删除
  5. 链表插入新节点
  6. 链表的数据排序
  7. 链表的反序
  8. 清空链表的元素
  9. 求链表的长度等

这章我们讲链表的节点数统计与链表数据查找替换 

上章代码

#include <stdio.h>
 
struct Link
{
    int data;
    struct Link *next;
};
 
void PrintLink(struct Link *head)
{
    struct Link *prev = head;
    while (NULL != prev) 
    {
        printf("%d  ", prev->data);
        prev = prev->next;
    }
    printf("\n");
}
 
int main()
{
    struct Link link1 ={1,NULL};
    struct Link link2 ={2,NULL};
    struct Link link3 ={3,NULL};
 
    link1.next = &link2;
    link2.next = &link3;
    link3.next = NULL;
 
    PrintLink(&link1);
    return 0;
}

01 链表的节点数统计

统计链表的节点个数,其实这个就很简单,和上一章的遍历输出是一个道理,我们拿上面的代码改一下。

我们现在要统计节点数,那可能要用到这个节点的数目,所以我们定义一个int 返回型的函数

int GetLinkNum(struct Link *head)
{

}

然后我们需要个整形数记录节点数

所以int count = 0;

我们就用count记录节点的数目,然后遍历,while每循环一次,count++

int GetLinkNum(struct Link *head)
{
    struct Link *prev = head;
    int count = 0;
    while (prev != NULL)
    {
        count++;
        prev = prev->next;
    }
    return count;
}

大概就是这样了,最后返回的是链表的节点数目 

02 链表数据查找替换 

2.1 残疾的数据查找

刚刚我们实现了统计链表的节点数,现在我们尝试一下通过遍历查找数据是否存在,我们先思考一下,查找函数,如果我们找到了数据,我们想做什么呢?

我们可以试着让它返回0或1,0为未找到数据 1则找到数据,如果可以的话,可以写成宏定义,TURE或FLASE

int findLinkData(struct Link *head,int data)
{
    struct Link *prev = head;
    while (prev!= NULL)
    {
        if (prev->data == data)
        {
            return 1;
        }
        prev = prev->next;
    }
    return 0;
}

我们定义个函数,函数名为findLinkData,返回值类型为int,我们让链表进行遍历

然后if语句查找data,如果有相同的数据则返回1,否则链表遍历到链表尾也没有相同的数据的话,那就返回0 

 可以看到,函数是可以找到查找需要的数据的

但是代码还是有点残疾,比如我链表好多个数据都是2呢?

那它找到最近的就返回了,那怎么行呢?

2.2 数据查找优化

现在我不单单要查找数据,还要将数据和所在节点号输出来,如何做到呢?

其实节点号的话直接在结构体里多加一项数据记录每个节点的节点号也可以,但我们

在案例就不那么做了

void FindLinkDataPro(struct Link *head,int data)
{
   int count = 0;     //遍历记录节点号
   int NumFd =0;   // Number数据的索引
   int Number[32] = {0};
   struct Link *prev = head;
   while (prev!= NULL)
   {
        if(prev->data == data)
        {
            Number[NumFd++] = count;
        }
        count++; 
        prev = prev->next;
   }
    for(int i = 0; i < NumFd; i++)
    {
        printf("节点号:%d  查找的数据%d\n",Number[i]+1,data);
    }
}

这个是函数体,首先我的方法是,当找到需要查找的数据时,我定义一个数组来接收节点号,并保存下来,当遍历完链表后,我在统一输出来

 

现在我定义了四个节点,其中2和4的数据为2,然后我让FindLinkDataPro进行查找

 

可以看到,没有任何问题,还有就是数据的替换了,其实更简单了,我们到都能找到了,那么直接将内存写入的输入重新写入就好,所以就不讲解了,如果需要讲解的话可以私信我

例题源码

#include <stdio.h>

struct Link
{
    int data;
    struct Link *next;
};

void PrintLink(struct Link *head)
{
    struct Link *prev = head;
    while (NULL != prev) 
    {
        printf("%d  ", prev->data);
        prev = prev->next;
    }
    printf("\n");
}

int GetLinkNum(struct Link *head)
{
    struct Link *prev = head;
    int count = 0;
    while (prev != NULL)
    {
        count++;
        prev = prev->next;
    }
    return count;
}

int findLinkData(struct Link *head,int data)
{
    struct Link *prev = head;
    while (prev!= NULL)
    {
        if (prev->data == data)
        {
            return 1;
        }
        prev = prev->next;
    }
    return 0;
}

void FindLinkDataPro(struct Link *head,int data)
{
   int count = 0;     //遍历记录节点号
   int NumFd =0;   // Number数据的索引
   int Number[32] = {0};
   struct Link *prev = head;
   while (prev!= NULL)
   {
        if(prev->data == data)
        {
            Number[NumFd++] = count;
        }
        count++; 
        prev = prev->next;
   }
    for(int i = 0; i < NumFd; i++)
    {
        printf("节点号:%d  查找的数据%d\n",Number[i]+1,data);
    }
}

int main()
{
    struct Link link1 ={1,NULL};
    struct Link link2 ={2,NULL};
    struct Link link3 ={3,NULL};
    struct Link link4 ={2,NULL};

    link1.next = &link2;
    link2.next = &link3;
    link3.next = &link4;
    link4.next = NULL;

    PrintLink(&link1);
    FindLinkDataPro(&link1,2);
    //int findID = 0;
    //findID = findLinkData(&link1,2);
    //printf("findID = %d           0为未找到数据 1则找到数据\n", findID);
    //printf("%d\n", GetLinkNum(&link1));
    return 0;
}

  • 28
    点赞
  • 22
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

@ChenPi

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值