C语言复习和刷题 11.1

目录

链表复习

链表的创建

链表的修改

链表的删除

刷题

1⃣️

​​​​​​​

2⃣️


 

链表复习

链表的创建

typedef struct student{
        int score;
        struct student *next; 
}Linklist;

//n为需要输入的个数,解决了不能int a[n]的问题

LinkList *creat(int n){
	LinkList *head, *node, *end;//定义头节点,普通节点,尾部节点;
	head = (LinkList*)malloc(sizeof(LinkList));//分配地址
	end = head;         //若是空链表则头尾节点一样
	for (int i = 0; i < n; i++) {
		node = (LinkList*)malloc(sizeof(LinkList));
		scanf("%d", &node->score);
		end->next = node;
		end = node;
	}
	end->next = NULL;//结束创建
	return head;
}

或者用 do while 的形式,读取到-1时结束,不用再去定义大数组或者担心数组不够大的问题

LinkList *creat(){
	LinkList *head, *node, *end;//定义头节点,普通节点,尾部节点;
	head = (LinkList*)malloc(sizeof(LinkList));//分配地址
	end = head;      //若是空链表则头尾节点一样
	do{
	node = (LinkList*)malloc(sizeof(LinkList));
		scanf("%d", &node->score);
		end->next = node;
		end = node;
	}while(&node->score != -1)
	end->next = NULL; //结束创建
	return head;
}

链表的修改

void change(LinkList *list,int n) //n为第n个节点 
{
	LinkList *t = list;
	int i = 0;
	while (i < n && t != NULL) 
    {
		t = t->next;
		i++;
	}
	if (t != NULL) 
    {
		puts("输入要修改的值");
		scanf("%d", &t->score);
	}
	else {
		puts("节点不存在");
	}
}

链表的删除

void delete(LinkList *list, int n)//n为链表里有多少个节点 
{
	LinkList *t = list, *de;
	int i = 0;
	while (i < n && t != NULL) {
		de = t;
		t = t->next;
		i++;
	}
	if (t != NULL) {
		de->next = t->next;
		free(t);
	}
	else {
		puts("节点不存在");
	}
}

刷题

1⃣️

L1-005 考试座位号 (15 分)

每个 PAT 考生在参加考试时都会被分配两个座位号,一个是试机座位,一个是考试座位。正常情况下,考生在入场时先得到试机座位号码,入座进入试机状态后,系统会显示该考生的考试座位号码,考试时考生需要换到考试座位就座。但有些考生迟到了,试机已经结束,他们只能拿着领到的试机座位号码求助于你,从后台查出他们的考试座位号码。

输入格式:

输入第一行给出一个正整数 N(≤1000),随后 N 行,每行给出一个考生的信息:准考证号 试机座位号 考试座位号。其中准考证号由 16 位数字组成,座位从 1 到 N 编号。输入保证每个人的准考证号都不同,并且任何时候都不会把两个人分配到同一个座位上。

考生信息之后,给出一个正整数 M(≤N),随后一行中给出 M 个待查询的试机座位号码,以空格分隔。

输出格式:

对应每个需要查询的试机座位号码,在一行中输出对应考生的准考证号和考试座位号码,中间用 1 个空格分隔。

输入样例:

4
3310120150912233 2 4
3310120150912119 4 1
3310120150912126 1 3
3310120150912002 3 2
2
3 4

结尾无空行

输出样例:

3310120150912002 2
3310120150912119 1

结尾无空行

//主要用到了二维数组的知识

#include<stdio.h>

int main()
    {
        long int a[1000][3];
        int n;
        int m;
        int b[1000];
        scanf("%d",&n);
        for(int i=0;i<n;i++)
            {
                for(int l=0;l<3;l++)
                    {
                    scanf("%ld",&a[i][l]);
            
                    }
            }
        
        scanf("%d",&m);
        for(int j=0;j<m;j++)
            {
                scanf("%d",&b[j]);
            }
        for(int k=0;k<m;k++)
            {
                
                for(int i=0;i<n;i++)
                    {
                        if(b[k]==a[i][1])
                            {
                                printf("%ld %ld\n",a[i][0],a[i][2]);
                            }
                    }
            }
        return 0;
    }

2⃣️

7-38 数列求和-加强版 (20 分)

给定某数字A(1≤A≤9)以及非负整数N(0≤N≤100000),求数列之和S=A+AA+AAA+⋯+AA⋯A(N个A)。例如A=1, N=3时,S=1+11+111=123。

输入格式:

输入数字A与非负整数N。

输出格式:

输出其N项数列之和S的值。

输入样例:

1 3

结尾无空行

输出样例:

123

结尾无空行

本题的方法将类似于1 ,11,111,1111……分别存入数组再相加,但有很大的缺点,数组会占用大量的内存,并且当题目中的N较大时对计算机要求很高,而且结果会超出整形范围,这种代码无法通过测试。
#include<stdio.h>

int main()
    {
        int a,b;
        int sum=0;
        scanf("%d %d",&a,&b);
        int c[100000];
        if(b<0||b>100000)
            {
                return 0;
            }
        for(int i=0;i<b;i++)
            {
                int index=0;
                for(int k=0;k<i+1;k++)
                    {
                    index =index*10+a;
                    c[i]=index;
                    }
                
            }
        //for(int i=0;i<b;i++)
        //    {
        //        printf("%d\n",c[i]);
        //    }
        for(int i=0;i<b;i++)
            {
                sum+=c[i];
            }
        printf("%d",sum);
        return 0;
        
    }

改进后的代码

那我们就用最简单的方法,直接用加法,但是我们要将每一位上的数字存入数组里面,再输出数组,这样子的效率会高很多。思路来源于:7-38 数列求和-加强版 (20分)_King-CSDN博客

#include<stdio.h>

int main()
    {
        int a,n;
        int b[100000]={0};
        int plus=0;
        int cnt=0;
        int sum=0;
        int k=0;
        int flag=1;
        scanf("%d%d",&a,&n);
        if(n<0||n>100000)
            {
                return 0; 
            }
        if(n==0)
            {
                printf("0");
                return 0;
            }
        for(int i=n;i>=0;i--)
            {
                sum=a*(n-cnt);
                //printf("i=%d ",i);
                sum+=plus;
                b[i-1]=sum%10;
                plus=sum/10;
                //printf("sum=%d b[%d]=%d plus=%d\n",sum,i-1,b[i-1],plus);
                sum=0;
                cnt++;
            }
        for(int i=0;i<n;i++)
            {
                if(flag && b[cnt] == 0)
		            {
			        flag = 0;
			        continue;
		            }
		
                printf("%d",b[i]);
            }
        return 0;
    }

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值