链表基础知识

/*使用链表实现一个学生信息管理系统。要求:学生有名字(string)、平均成绩(double)、学号(string)三个属性。
 实现以下函数:
 ①、插入一条学生信息,并且保证链表有序,成绩高的靠近链表头。
 ②、根据名字查询所有同名的学生信息,打印出来
 ③、实现查询平均成绩在某一区间内的学生个数
 ④、根据学号删除一条学生信息
 ⑤、根据学号修改某一个学生的平均成绩,并保持链表有序。(tip:拿出来重新插入一次就可以了))*/
#include <cstdio>
#include <string>
using namespace std;
#define null NULL
struct student{
    string name;
    double score;
    string num;
};
struct node{
    node* nxt;
    student n;
};
node* createnode()//创建一个结点
{
    node* x =null;//初始化NULL或者直接申请内存
    x= new node();
    x->nxt=null;
    return x;
}
void insert(node* head,node* cur)//把结点插入链表
{
    node* pre =head;
    node* p = head->nxt;
    // head-> node1 -> node2 -> node3 -> ...
    //  pre     p
    while(p)
    {
        if(p->n.score < cur->n.score)
        {
            //   ... -> pre -> p -> nodex -> ...
            // ...-> pre -> cur -> p -> nodex -> ...
            cur->nxt = p;
            pre->nxt = cur;
            return;
        }
        pre = p;
        p = p->nxt;
    }
    // p == NULL
    // ...->pre -> p(NULL)
    pre->nxt =cur;
}
//   错误示范 node* temp;
//    if(p==null)
//    {
//        p=cur;
//        cur->nxt=null;
//    }
//    else
//    {
//        if((p->n.score)<(cur->n.score))
//        {
//            // cur-> p
//            // head-> p
//            cur->nxt=p;
//            p=cur;
//        }
//        else
//        {
//            while(p!=null&&(p->n.score)>(cur->n.score))
//            {
//                temp=p;
//                p=p->nxt;
//            }
//            cur->nxt=temp->nxt;
//            temp->nxt=cur;
//        }
//    }
node* querynode(node* head,string name)
{
    node* cur=head->nxt;
    while(cur)
    {
        if(cur->n.name==name)
        {
            return cur;
        }
        cur=cur->nxt;
    }
    return null;
}
int queryscope(node* head,double score1,double score2)
{
    node* cur=head->nxt;
    int n=0;
    while(cur)
    {
        if((cur->n.score)>score1&&(cur->n.score)<score2)
            n++;
        cur=cur->nxt;
    }
    return n;
}
void deletenode(node* head,string num)
{
    node* pre=head;
    node* cur=head->nxt;
    while(cur)//遍历
    {
        if(cur->n.num==num)
        {
            pre->nxt=cur->nxt;//将cur的后继赋值给pre的后稷
            delete cur;//让系统回收此结点,释放内存
            break;
        }
        pre=cur;
        cur=cur->nxt;
    }
}
node* change(node* head,string num,double gradeavg)
{
    node* pre = head;
    node* cur=head->nxt;
    while(cur)
    {
        if(cur->n.num==num)
        {
            // head-> ... -> pre -> cur -> nodex -> ...->
            cur->n.score=gradeavg;
            pre->nxt=cur->nxt;
// 错误示范           p->n.name=cur->n.name;
//            p->n.score=cur->n.score;
//            p->n.num=cur->n.num;
//            deletenode(head, num);
            // head-> ... -> pre -> nodex -> ...->
            insert(head,cur);
            // head-> ... -> pre -> nodex -> ...-> cur -> ...
            return cur;
        }
        pre = cur;
        cur=cur->nxt;
    }
    return null;
}
void printfNode(node* head)
{
    node* temp = head->nxt;
    while(temp)
    {
        printf("%s %lf %s\n",temp->n.name.c_str(),temp->n.score,temp->n.num.c_str());
        temp=temp->nxt;
    }
}
int main()
{
    node* head =createnode();//建一个带头结点的单链表
    int a;
    printf("输入想要实现的功能:\n1.输入功能\n2.查询功能\n3.查询分数功能\n4.删除功能\n5.修改功能\n");
    while(scanf("%d",&a))
    {
        if(a==1)
        {
            char name[20],num[20];
            double score;
            printf("输入学生信息:\n");
            scanf("%s%lf%s",name, &score, num);
            node* cur=null;
            cur=createnode();
            cur->n.name=name;
            cur->n.score=score;
            cur->n.num=num;
            insert(head,cur);
        }
        else if(a==2)
        {
            char name[20];
            printf("输入要查寻的姓名:\n");
            scanf("%s",name);
            node* que=null;
            que=querynode(head,name);
            if(que==null)
            {
                printf("not found\n");
                continue;
            }
            student& v=que->n;
            printf("%s%lf%s\n",v.name.c_str(),v.score,v.num.c_str());
        }
        else if(a==3)
        {
            double score1,score2;
            int m;
            printf("输入要查寻的分数区间:\n");
            scanf("%lf%lf",&score1,&score2);
            m=queryscope(head,score1,score2);
            printf("%d\n",m);
        }
        else if(a==4)
        {
            char num[20];
            printf("输入要删除的学号:\n");
            scanf("%s",num);
            deletenode(head,num);
        }
        else if(a==5)
        {
            char num[20];
            double gradeavg;
            printf("输入要修改的学号:\n");
            scanf("%s%lf",num,&gradeavg);
            change(head,num,gradeavg);
        }
        printfNode(head);
    }
}

循环链表:单链表中终端结点的指针端由空指针改为指向头结点

//循环列表的判断方法(追及问题)
#include <cstdio>
#define null NULL;
using namespace std;
struct node
{
    node* nxt;
    int n;
};
int main()
{
    node* head=null;
    node* x1=head;
    node* x2=head;
    while(x1&&x2)
    {
        x1=x1->nxt;//x1向后移动一次
        x2=x2->nxt;
        if(x2)
            x2=x2->nxt;//x2向后移动两次
        else
            break;
        if(x1==x2)//循环链表就会有x2=x1的时候
        {
            printf("yes\n");
            break;
        }
    }
}

//错误判断方法,该方法只适用于判断头尾相接的链表
#include <cstdio>
#define null NULL
using namespace std;
struct node{
    node* nxt;
    int n;
};
int main()
{
    node* head=null;
    node* cur=head->nxt;
    while(cur)
    {
        cur=cur->nxt;
        if(cur==head)
            printf("yes\n");
        else
            break;
    }
}

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值