当前位置:   article > 正文

ZISUOJ C语言-综合练习

ZISUOJ C语言-综合练习

说明:

博主是ZISU在校学生,刚学C/C++才3个月,为了记录自己的学习过程和分享思路,故写一些博客。当然我的代码许多时候不是最优解,欢迎大家评论留言一起学习。如果有友友想提交这些题试试自己的思路啥的,可以私我,因为外校友友应该是登陆不进咱们的平台的。对于搜索到本博客的同校友友,切勿直接照抄,理解了再自己码字码上去。

题目列表:

 问题 A: 二进制中1的个数

思路:先计算每个数的二进制1的个数,然后循环打擂台找最大的二进制1的个数,再循环找第一个出现跟前面个数相等的下标,输出对应下标的数即可

参考题解:

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. const int N = 1e2+5;//N=(int)105
  4. struct number{
  5. int num,num_of_binary_one;//num为数值,num_of_binary_one为该数值对应的含有的二进制1的个数
  6. }a[N];
  7. int cal_num_of_binary_one(int num1){//计算num1含有的二进制1的个数
  8. int count = 0;
  9. while(num1!=0){
  10. if(num1%2==1) count++;
  11. num1/=2;
  12. }
  13. return count;
  14. }
  15. int main(){
  16. //问题 A: 二进制中1的个数
  17. ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);//要用scanf()和printf()不能使用快读
  18. int n;cin >> n;
  19. for(int i = 1;i<=n;i++) cin >> a[i].num;
  20. //计算数值对应的含有的二进制1的个数
  21. for(int i = 1;i<=n;i++) a[i].num_of_binary_one = cal_num_of_binary_one(a[i].num);
  22. int maxone = 0;//maxone找所有数中最多的二进制1的个数
  23. for(int i = 1;i<=n;i++) if(a[i].num_of_binary_one > maxone) maxone = a[i].num_of_binary_one;
  24. int maxindex = 1;//记录结果的下标
  25. //遍历查询,如果找到第一个二进制1的个数跟maxindex相等的记录下它的下标并跳出循环
  26. for(int i = 1;i<=n;i++){
  27. if(a[i].num_of_binary_one == maxone){
  28. maxindex = i;break;
  29. }
  30. }
  31. cout << a[maxindex].num << '\n';
  32. return 0;
  33. }

问题 B: 最新版消消乐

 

思路:遍历输入的字符串,有两个重复的字符则只输出一次,其余情况正常输出即可

参考题解:

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. const int N = 1e2+5;
  4. char s[N];
  5. int main(){
  6. //问题 B: 最新版消消乐
  7. ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);//要用scanf()和printf()不能使用快读
  8. cin >> s;
  9. int i = 0;//i为s的下标
  10. while(i<strlen(s)){//下标i遍历s
  11. if(s[i]==s[i+1]&&i<strlen(s)-1){//如果有两个重复字母,则只输出一次
  12. cout << s[i];
  13. i+=2;
  14. }else{//正常输出
  15. cout << s[i];
  16. i++;
  17. }
  18. }
  19. cout << '\n';
  20. return 0;
  21. }

问题 C: 组合数

说明:依据题意写一个求组合数C(n,m)的函数计算即可

参考题解:

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. using ll = unsigned long long;//使用ll代替unsigned long long
  4. ll factorial(int num){//计算阶乘函数
  5. ll res = 1;
  6. for(int i = 1;i<=num;i++) res*=i;
  7. return res;
  8. }
  9. ll C(int n,int m){//计算组合数函数
  10. return (factorial(n)/factorial(n-m))/factorial(m);
  11. }
  12. int main(){
  13. //问题 C: 组合数
  14. ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);//要用scanf()和printf()不能使用快读
  15. int n,m;
  16. while(cin >> n >> m){//没有输入则跳出循环
  17. cout << C(n,m) << '\n';//输出所求组合数答案
  18. }
  19. return 0;
  20. }

问题 D: 费马平方和定理

 

 思路:根据定理的说明,先判断该范围内模4余1的数是否为素数,如果为素数再开始暴力寻找对应的平方和

参考题解:

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. bool is_Prime(int num){//判断是否为素数,为素数则返回true,否则返回false
  4. if(num <= 1) return false;
  5. for(int i = 2;i*i<=num;i++){
  6. if(num%i==0) return false;
  7. }
  8. return true;
  9. }
  10. int main(){
  11. //问题 D: 费马平方和定理
  12. ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);//要用scanf()和printf()不能使用快读
  13. int n;cin >> n;
  14. for(int i = 5;i<=n;i+=4){//i的步长为4
  15. if(is_Prime(i)){//如果为素数,则开始找满足i的费马平方和定理
  16. int type = 0;//type为1则表示以及找到i的费马平方和定理的公式了,type为0则表示暂时还没找到
  17. for(int j = 1;j*j<=i;j++){
  18. for(int k = sqrt(i-1);k>=1;k--){
  19. if(j*j+k*k==i){
  20. //格式化输出
  21. cout << i << '=' << j << "**2+" << k << "**2" << '\n';
  22. type = 1;
  23. break;
  24. }
  25. }
  26. if(type) break;//type为1跳出循环
  27. }
  28. }
  29. }
  30. return 0;
  31. }

问题 E: 成绩排名1

说明:开一个student结构体,存放student的学号和总分,使用sort()函数先按照总分从高到低排序,如果总分相同则按照学号从小到大排序,最后输出即可

参考题解:

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. const int N = 1e4+5;
  4. struct student{
  5. string number;//学号
  6. int score;//总分成绩
  7. }stu[N];
  8. bool cmp(student stu1,student stu2){
  9. //按照总分成绩从高到低排序
  10. if(stu1.score!=stu2.score) return stu1.score>stu2.score;
  11. //如果总分成绩相同,则按照学号从小到大排序
  12. else return stu1.number<stu2.number;
  13. }
  14. int main(){
  15. //问题 E: 成绩排名1
  16. ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);//要用scanf()和printf()不能使用快读
  17. int n;cin >> n;
  18. //读入每个学生学号和总分成绩
  19. for(int i = 1;i<=n;i++) cin >> stu[i].number >> stu[i].score;
  20. sort(stu+1,stu+1+n,cmp);//从stu[1]到stu[n]按照cmp规则排序
  21. //格式化输出
  22. for(int i = 1;i<=n;i++) cout << stu[i].number << ' ' << stu[i].score << '\n';
  23. return 0;
  24. }

 问题 F: 成绩排名2

 

说明:与上面一题思路同理,计算出每个学生的总成绩并按照总成绩从高到低排序,如果总成绩相同,则按照学号从小到大排序,同时还需要计算出每个学生所有题目中的单题最高成绩,最后按顺序输出学号和单题最高成绩即可。

参考题解:

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. const int N = 1e4+5;
  4. struct student{
  5. string number;//学号
  6. int m,total_score,max_score;//m为做出的题目数,total_score为总分,max_score为单题最高分
  7. int score[15];//各个题目的成绩
  8. }stu[N];
  9. bool cmp(student stu1,student stu2){
  10. //按照总分成绩从高到低排序
  11. if(stu1.total_score!=stu2.total_score) return stu1.total_score>stu2.total_score;
  12. //如果总分成绩相同,则按照学号从小到大排序
  13. else return stu1.number<stu2.number;
  14. }
  15. int main(){
  16. //问题 E: 成绩排名1
  17. ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);//要用scanf()和printf()不能使用快读
  18. int n;cin >> n;
  19. //读入每个学生学号和总分成绩
  20. for(int i = 1;i<=n;i++){
  21. cin >> stu[i].number >> stu[i].m;
  22. int sum = 0;//暂存当前数量题目得分的累加和
  23. for(int j = 1;j<=stu[i].m;j++){
  24. cin >> stu[i].score[j];
  25. sum += stu[i].score[j];
  26. }
  27. //赋值该学生的总分,给单题最高分赋初始值
  28. stu[i].total_score = sum,stu[i].max_score = 0;
  29. //打擂台找单题最高分
  30. for(int j = 1;j<=stu[i].m;j++) if(stu[i].score[j]>stu[i].max_score) stu[i].max_score = stu[i].score[j];
  31. }
  32. sort(stu+1,stu+1+n,cmp);//从stu[1]到stu[n]按照cmp规则排序
  33. //输出
  34. for(int i = 1;i<=n;i++) cout << stu[i].number << ' ' << stu[i].max_score << '\n';
  35. return 0;
  36. }

问题 G: 纠结的PP

说明:贪心思想,把鞋子按照重量从小到大排序,能拿当前最轻的鞋子就拿最轻的,拿不了就输出结果

参考题解:

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. const int N = 1e4+5;
  4. const int MAX = 3000;
  5. struct shoes{
  6. string name;//鞋名
  7. int weight;//鞋的重量
  8. }shoe[N];
  9. bool cmp(shoes shoe1,shoes shoe2){
  10. //按鞋的重量从小到大排序
  11. return shoe1.weight<shoe2.weight;
  12. }
  13. int main(){
  14. //问题 G: 纠结的PP
  15. ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);//要用scanf()和printf()不能使用快读
  16. int n;cin >> n;
  17. //读鞋的鞋名和鞋的重量
  18. for(int i = 1;i<=n;i++) cin >> shoe[i].name >> shoe[i].weight;
  19. sort(shoe+1,shoe+1+n,cmp);//从shoe[1]到shoe[n]按照cmp规则排序
  20. int now_weight = 0,now_num = 0;//now_weight为当前重量,now_num为当前鞋子的双数
  21. for(int i = 1;i<=n;i++){//贪心
  22. //能拿最轻的鞋子就先拿最新的鞋子
  23. if(now_weight+shoe[i].weight<=MAX){
  24. //累加当前重量
  25. now_weight += shoe[i].weight;
  26. //鞋子双数加1
  27. now_num++;
  28. }else break;//拿不了就跳出循环
  29. }
  30. if(!now_num) cout << ":(" << '\n';//一双都拿不了输出":("
  31. else cout << now_num << '\n';//能拿几双输出几双
  32. return 0;
  33. }

问题 H: 七七七

 

说明:同理,开结构体存放弹幕字符串,弹幕的长度,弹幕含7的个数,然后按照题目描述的要求排序输出即可

参考题解:

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. const int N = 1e4+5;
  4. struct barrage{
  5. string str;//弹幕字符串
  6. int len;//弹幕字符串的长度
  7. int num_of_seven;//弹幕中'7'的个数
  8. }b[N];
  9. int cal_num_of_seven(barrage b){//计算弹幕中'7'的个数
  10. int res = 0;
  11. for(int i = 0;i<b.len;i++) if(b.str[i]=='7') res++;
  12. return res;
  13. }
  14. bool cmp(barrage b1,barrage b2){
  15. //包含数字"7"多的排在前面
  16. if(b1.num_of_seven!=b2.num_of_seven) return b1.num_of_seven>b2.num_of_seven;
  17. //如果两句弹幕包含一样多的"7",则按照长度从小到大排
  18. else if(b1.num_of_seven==b2.num_of_seven&&b1.len!=b2.len) return b1.len<b2.len;
  19. //如果长度仍然一样,则按照字典序大的排在前面
  20. else return b1.str>b2.str;
  21. }
  22. int main(){
  23. //问题 H: 七七七
  24. ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);//要用scanf()和printf()不能使用快读
  25. int n;cin >> n;
  26. for(int i = 1;i<=n;i++){
  27. cin >> b[i].str;//读入弹幕的字符串
  28. b[i].len = b[i].str.length();//计算弹幕字符串的长度
  29. //计算弹幕字符串中'7'的个数
  30. b[i].num_of_seven = cal_num_of_seven(b[i]);
  31. }
  32. sort(b+1,b+1+n,cmp);//从b[1]到b[n]按照cmp规则排序
  33. //输出
  34. for(int i = 1;i<=n;i++) cout << b[i].str << '\n';
  35. return 0;
  36. }

问题 I: 排名次

说明:同理,使用结构体存放姓名和成绩,按照成绩从高到低排序,如果成绩相同,则把名字按照字典顺序排序,输出排序后的结果即可

参考题解:

  1. #include <bits/stdc++.h>
  2. using namespace std;
  3. const int N = 1e3+5;
  4. struct student{
  5. string name;//学生姓名
  6. int score;//学生成绩
  7. }stu[N];
  8. bool cmp(student stu1,student stu2){
  9. //按成绩(分数)从高分到低分的顺序排名
  10. if(stu1.score!=stu2.score) return stu1.score>stu2.score;
  11. //如果成绩(分数)相同则按姓名进行排序(字典顺序)
  12. else return stu1.name<stu2.name;
  13. }
  14. int main(){
  15. //问题 I: 排名次
  16. ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);//要用scanf()和printf()不能使用快读
  17. int n;cin >> n;
  18. //读入学生姓名和分数
  19. for(int i = 1;i<=n;i++) cin >> stu[i].name >> stu[i].score;
  20. sort(stu+1,stu+1+n,cmp);//从stu[1]到stu[n]按照cmp规则排序
  21. for(int i = 1;i<=n;i++) cout << stu[i].name << ' ' << stu[i].score << '\n';
  22. return 0;
  23. }
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/IT小白/article/detail/426304
推荐阅读
相关标签
  

闽ICP备14008679号