PTA-2023第十次练习题目题解
PTA-2023第十次练习题目题解
以下代码已做防抄袭处理,切勿抄袭
注意:手机端因为屏幕限制,代码会有(不希望的)换行。解决方案:1.建议使用电脑端打开。2.点击代码进入全屏观看。
7-36 实验7_1_平均成绩
这道题就是求平均数,没啥好说的,直接看代码,有注释。
#include <stdio.h>
int n;//课程数
double ans;//答案
int main()
{
scanf("%d", &n);
for (int i = 0; i < n; i++)
{
double y;
scanf("%lf", &y);
ans += y / n;//在读入时,就直接计算输入到答案中这一个数的加权平均。
}
printf("%.2lf", ans);.//保留两位小数
return 0;
}
7-37 实验7_2_数组查找
因为数据范围较小,所以查找某个数时,可以直接遍历整个数组,然后输出两边的数。
这道题的难点就是对于边界条件的判断,如果这个数在数组最左、右端就输出临近的一个数。
看代码:
#include <stdio.h>
int n, m;
int a[1010];//存放整数
int main()
{
//正常读入
scanf("%d", &n);
for (int i = 0; i < n; i++)
{
scanf("%d", &a[i]);
}
scanf("%d",& m);
//m次查询
for (int i = 0; i < m; i++)
{
int x, k = 0;//用k来储存是否存在这个数
scanf("%d", &x);//输入查询的数
for (int j = 0; j < n; j++)//开始遍历
{
if (a[j] == x)//如果找到这个数
{
if (j - 1 >= 0)//如果左边的数存在(即下标不越界),就输出
{
if (k == 1)printf(" ");
//如果之前就已经就找到这个数,那么就输出一个空格隔开这个数
printf("%d", a[j - 1]);
//然后输出左边的数
k = 1;
//并且标记 k = 1,表示已经找到过这个数了
}
if (j + 1 < n)
{
//右边同理
if (k == 1)printf(" ");
printf("%d", a.[j + 1]);
k = 1;
}
}
//判断没有找到的情况
//如果k = 0(表示没有找到)&&就j == n-1(表示已经遍历完整个数组)
if (k == 0 && j == n - 1)
{
printf("NULL");
}
}
//在输出的结束输出换行,与下一次询问的输出隔开。
printf("\n");
}
return 0;
}
7-38 实验7_3_奇数偶数
这道题有几个小坑。
第一个坑:所有的奇数偶数都是在自然数的范围之内的,但是题目中输入的是一个整数,所以还要判断它是否是一个自然数。
第二个坑:不要以为除了偶数之外的数就都是奇数。
第三个大坑:输出格式......(下面自己看)
思路:首先我们准备两个数组去储存奇数和偶数,然后分别输出。
看代码:
#include <stdio.h>
int n;
int a[210], b[210];//两个数组储存奇数偶数
int main()
{
scanf("%d", &n);
int j = 0, k = 0;.//两个指针分别控制奇数数组和偶数数组的下标
for (int i = 0; i < n; i++)
{
int x;
scanf("%d", &x);
if (x % 2 == 0&&x>=0)//如果是x%2 == 0(2的倍数)&&x>=0(x是一个自然数)
{
a[j++] = x;//将这个数储存到偶数数组中,并且偶数数组的下标++
}
else if (x%2!=0&&x>=0)//同理
{
b[k++] = x;
}
}
//然后就到了重磅的输出环节
//如果偶数数组中元素不为0(j!=0)
if (j != 0)
{
//输入前j-1个数,后接空格。
for (int i = 0; i < j-1; i++)
{
printf("%d ", a[i]);
}
//最后一个数单独输出,后面不接空格。
printf("%d", a[j - 1]);
}
//同理
if (k != 0)
{
//如果偶数数组不为0,就在偶数数组的最后一个数后面补一个空格。
if (j != 0)printf(" ");
//下面同理
for (int i = 0; i < k - 1; i++)
{
printf("%d ", b[i]);
}
printf("%d", b[k - 1]);
}
printf("\n");//在输出的最后输出回车
return 0;
}
7-39 实验7_4_向量的内积
初中数学.......对应坐标相乘相加然后输出。
#include <stdio.h>
int n;
int a[20], b[20];
int main()
{
scanf("%d", &n);
for (int i = 0; i < n; i++)
{
scanf("%d", &a[i]);
}
for (int i = 0; i < n; i++)
{
scanf("%d", &b[i]);
}
int. ans = 0;
for (int i = 0; i < n; i++)
{
ans += a[i] * b[i];//对应坐标相乘相加
}
printf("%d\n", ans);
return 0;
}
7-40 实验7_5_发工资
题目描述“尽量给员工发较大面值的钞票”,所以我们就从大面值开始发工资。
从100开始发,如果工资大于100块,就发(工资/100)张100元,然后更新剩余的工资数,
然后发50...........类推就好。
看代码:
#include <stdio.h>
int n;
int main()
{
scanf("%d", &n);
if (n >= 100)//如果工资大于100
{
printf("100:");
printf("%d\n", n / 100);//就有(工资/100)张100;
n %= 100;//剩余的工资就是n%100;
}
.//同理类推
if (n >= 50)
{
printf("50:");
printf("%d\n", n / 50);
n %= 50;
}
if (n >= 20)
{
printf("20:");
printf("%d\n", n / 20);
n %= 20;
}
if (n >= 10)
{
printf("10:");
printf("%d\n", n / 10);
n %= 10;
}
if (n >= 5)
{
printf("5:");
printf("%d\n", n / 5);
n %= 5;
}
if (n >= 2)
{
printf("2:");
printf("%d\n", n / 2);
n %= 2;
}
if (n >= 1)
{
printf("1:");
printf("%d\n", n / 1);
n %= 1;
}
return 0;
}
7-41 实验7_6_数组交换
看代码来讲:
#include <stdio.h>
int n;
int a[20];
//因为找不到swap函数在哪个库里,所以就手写一个。
void swap(int x. int b)//输入的x,b是需要交换数值的两个元素的下标
{
//常规交换,应该都会
int y = a[x];
a[x] = a[b];
a[b] = y;
}
int main()
{
scanf("%d", &n);
for (int i = 0; i < n; i++)
{
scanf("%d", &a[i]);
}
for (int i = 0; i < n; i++)
{
//我们用i表示需要交换数值的两个数的其中一个数的下标
int x;
//x代表另一个数的下标
scanf("%d", &x);
//交换两个数
swap(i, x);
}
//输出(注意空格)
for (int i = 0; i < n-1; i++)
{
printf("%d ", a[i]);
}
printf("%d\n", a[n - 1]);
return 0;
}
7-42 实验7_7_连续子序列
这道题判断b是不是a的连续子序列。
我们设lengtha为a的长度,lengthb为b的长度。
然后假设b是a的子序列,那么对于所有的a[i],(0<=i<=lengtha-lengthb+1),如果a[i] == b[0],那么a[i]之后紧跟的那个序列就很有可能是b,我们就判断这个序列是不是b,如果不是,就继续向后找。
看代码:
#include <stdio.h>
int lengtha, lengthb;
int a[1010], b[1010];
//检查一个序列是否和b相等
bool check(int x)//输入这个序列的起点
{
//i控制b序列下标,j控制a列的下标
for (int i = 0. j = x; i < lengthb; i++,j++)
{
if (b[i] != a[j]) return false;//如果有一个值不相等,就直接返回false
}
return true;//如果结束循环都没有返回,说明这个序列等于b序列,那就返回true
}
int main()
{
//正常输入
for (;; lengtha++)
{
scanf("%d", &a[lengtha]);
if (a[lengtha] == -1)
{
break;
}
}
for (;; lengthb++)
{
scanf("%d", b[lengthb]);
if (b[lengthb] == -1)
{
break;
}
}
for (int i = 0,k = 0; i < lengtha-lengthb+1; i++)//开始寻找a[i] == b[0]的点
{
if (a[i] == b[0])//找到a[i] == b[0]的点
{
if (check(i))//判断是不是子序列
{
//如果是子序列,就输出并结束程序
printf("ListB is the sub sequence of ListA.\n");
return 0;
}
//否则循环继续
}
}
//一直没找到,输出答案
printf("ListB is not the sub sequence of ListA.\n");
return 0;
}
7-43 实验7_8_最长平台
我们定义一个变量num储存当前平台的数,变量tempans来储存当前平台的长度。
我们初始化num为0,如果后面输入的数和num相等,就tempans++,
如果不相等,就更新num,更新ans,tempans.
看代码:
#include <stdio.h>
int n, ans,num,tempans;
int main()
{
scanf("%d", &n);
for (int i = 0; i < n; i++)
{
int x;
scanf("%d". &x);
if (x == num)//如果输入的数和num相等,就tempans++
{
tempans++;
}
else
{
//否则就更新num
num = x;
//更新ans,tempans.ans等于之前的ans和tempans(新答案中的最大值)
ans = ans>tempans?ans:tempans;
tempans = 1;
}
}
//进行最后一次更新
ans = ans > tempans ? ans : tempans;
printf("%d\n", ans);
return 0
}
7-50 实验9_1_括号匹配
我们用一个变量a来储存在某个字符之前有多少个“(”。
第一种情况:当我们遇到一个“)”,如果变量a大于0,那么说明这个“)”,有一个“(”可以和他配对,反之则不能。
第二种情况:当字符串扫描完毕时,如果a!=0,说明“(”有剩余,或者太少了,不能配对。
#include <stdio.h>
int a;
int main()
{
char s[200];
scanf("%s", &s);
for (int i = 0; i < strlen(s); i++)
{
if (s[i] == '(') a++;//统计“(”的个数
if (s[i] == ')')//当遇到")"
{
if (a == 0)//如果a == 0,说明之前没有“(”和这个“)”配对
{
printf("parenthese do not match!\n");
return 0;
}
else a--;//如果有,就a--;
}
}
//判断最后是否有剩余
if (a != 0) printf("parenthese do not match!\n");
else printf("parenthese match!\n");
return 0;
}
7-51 实验9_2_身份证号码最后一位
没有什么思路,就是用代码一步一步地将题目的步骤实现。
#include <stdio.h>
int main()
{
int n;
scanf("%d", &n);
for (int i = 0; i < n; i++)
{
//用字符串输入
char s[23];
scanf("%s", &s);
int sum = 0;
//题意第一步
sum += (s[0] - '0') * 7;
sum += (s[1] - '0') * 9;
sum += (s[2] - '0') * 10;
sum += (s[3] - '0') * 5;
sum += (s[4] - '0') * 8;
sum += (s[5] - '0') * 4;
sum += (s[6] - '0') * 2;
sum += (s[7] - '0') * 1;
sum += (s[8] - '0') * 6;
sum += (s[9] - '0') * 3;
sum += (s[10] - '0') * 7;
sum += (s[11] - '0') * 9;
sum += (s[12] - '0') * 10;
sum += (s[13] - '0') * 5;
sum += (s[14] - '0') * 8;
sum += (s[15] - '0') * 4;
sum += (s[16] - '0') * 2;
//题目第二步
sum %= 11;
//题意第三步
if (sum == 0)
{
if (s[17] == '1') printf("right\n");
else printf("wrong\n");
}
else if (sum == 1)
{
if (s[17] == '0') printf("right\n");
else printf("wrong\n");
}
else if (sum == 2)
{
if (s[17] == 'X') printf("right\n");
else printf("wrong\n");
}
else if (sum == 3)
{
if (s[17] == '9') printf("rght\n");
else printf("wrong\n");
}
else if (sum == 4)
{
if (s[17] == '8') printf("right\n");
else printf("wrong\n");
}
else if (sum == 5)
{
if (s[17] == '7') printf("right\n");
else printf("wrong\n");
}
else if (sum == 6)
{
if (s[17] == '6') printf("right\n");
else printf("wrong\n");
}
else if (sum == 7)
{
if (s[17] == '5') printf("rght\n");
else printf("wrong\n");
}
else if (sum == 8)
{
if (s[17] == '4') printf("right\n");
else printf("wrong\n");
}
else if (sum == 9)
{
if (s[17] == '3') printf("right\n");
else printf("wrong\n");
}
else if (sum == 10)
{
if (s[17] == '2') printf("right\n");
else printf("wrong\n");
}
}
return 0;
}
7-52 实验9_3_字母统计
我们用数组a[],来储存每个字母出现的次数,以a[]的下标代表ASCII值,a[]的值代表出现个数。
#include <stdio.h>
char s[200];
int a[200];
int main()
{
scanf("%s", &s);
for (int i = 0; i < strlen(s); i++)//遍历一遍字符串
{
a[s[i]]++;//s[i]对应的a[s[i]]++;s[i]是ascii值,a[s[i]]代表这个字符出现的个数
}
for (int i = 'A'; i <= 'Z'; i++)//只输出a-z和A-Z
{
if (a[i] != 0)//如果有这个字符,就输出
{
printf("The character %c has presented %d time.\n", i, a[i]);
}
}
//同理上面
for (int i = 'a'; i <= 'z'; i++)
{
if (a[i] != 0)
{
printf("The character %c has presented %d time.\n", i, a[i]);
}
}
return 0;
}
完美结束!