LHL'PTA 实验3. 前8章实验综合训练(3)

实验3. 前8章实验综合训练(3)

7-1 计算平均成绩 (10分)
给定N个学生的基本信息,包括学号(由5个数字组成的字符串)、姓名(长度小于10的不包含空白字符的非空字符串)和成绩([0,100]区间内的整数),要求计算他们的平均成绩,并顺序输出平均线以下的学生名单。

输入格式:
输入在一行中给出正整数N(≤10)。随后N行,每行给出一位学生的信息,格式为“学号 姓名 成绩”,中间以空格分隔。

输出格式:
首先在一行中输出平均成绩,保留2位小数。然后按照输入顺序,每行输出一位平均线以下的学生的姓名和学号,间隔一个空格。

输入样例:
5
00001 zhang 70
00002 wang 80
00003 qian 90
10001 li 100
21987 chen 60

输出样例:
80.00
zhang 00001
chen 21987


#include<stdio.h>
#include<string.h>
//思路:构造学生结构体,结构体成员有学号(id),姓名(name),成绩(score),然后定义结构体数组,
//      用于存储每个学生的信息,然后通过引用结构体成员的成绩对结构体中的每一个数组元素进行操作。
 
struct student //构造学生结构体,即构造struct student这种数据类型
{
	char id[6];    //学号,由于题目要求五个数字组成的字符串所以需要申请足够的内存空间
	char name[11]; //姓名
	float score;   //成绩
};
 
int main()
{
	struct student stu[10]; //定义结构体数组,用于存储每一个学生的学号、姓名、成绩
	int i, N;
	float sum = 0, average;
	scanf("%d\n", &N);
	for (i = 0; i < N; i++) //循环读入学生信息
	{
		scanf("%s%s%f", &stu[i].id, &stu[i].name, &stu[i].score);
		sum += stu[i].score;
	}
	average = sum / N;
 //LHL'PTA 
	printf("%.2f\n", average);
	for (i = 0; i<N; i++)  //对学生成绩进行处理
	{
		if (stu[i].score < average)
		{
			printf("%s %s\n", stu[i].name, stu[i].id);
		}
	}
 
	return 0;


在这里插入图片描述
7-2 组织星期信息 (10分)
输入一个正整数repeat (0<repeat<10),做repeat次下列运算:

定义一个指针数组将下面的星期信息组织起来,输入一个字符串,在表中查找,若存在,输出该字符串在表中的序号,否则输出-1。

Sunday Monday Tuesday Wednesday Thursday Friday Saturday

输入输出示例:括号内为说明,无需输入输出

输入样例 (repeat=3) :
3
Tuesday
Wednesday
year

输出样例:
3
4
-1

#include<stdio.h>
#include<string.h>
int main()
{
int i,ri,repeat;
char *date[10]={“Sunday”,“Monday”,“Tuesday” ,“Wednesday”,“Thursday”,“Friday”,“Saturday”};
char str[80];

scanf("%d",&repeat);
getchar();
for(ri=1;ri<=repeat;ri++){
scanf("%s",str);
//LHL'PTA 
for( i=0;i<7;i++ ){

if ( !strcmp( date[i] , str ) )///字符串的比较
break ;}
if ( i >= 7 )
printf("-1\n");
else
printf("%d\n" , i+1 );
}
}

7-3 删除重复字符 (10分)
本题要求编写程序,将给定字符串去掉重复的字符后,按照字符ASCII码顺序从小到大排序后输出。

输入格式:
输入是一个以回车结束的非空字符串(少于80个字符)。

输出格式:
输出去重排序后的结果字符串。

输入样例:
ad2f3adjfeainzzzv

输出样例:
23adefijnvz

#include <stdio.h>
const int num= 256;
int main()
{
    char str[num];
    char *p = str;
    fgets(str,n,stdin);//字符串中含有回车
    int array[n] = {0};//定义大小为256的数组
    while(*p!='\n')
    {//LHL'PTA 
        array[*p]++;//记录每个字符出现的次数
        p++;
    }
    int i = 0;
    while(i<num)
    {
        if(array[i])
		{
            printf("%c",i);
        }
        i++;
    }
    return 0;
}

7-4 英文单词排序 (10分)
本题要求编写程序,输入若干英文单词,对这些单词按长度从小到大排序后输出。如果长度相同,按照输入的顺序不变。

输入格式:
输入为若干英文单词,每行一个,以#作为输入结束标志。其中英文单词总数不超过20个,英文单词为长度小于10的仅由小写英文字母组成的字符串。

输出格式:
输出为排序后的结果,每个单词后面都额外输出一个空格。

输入样例:
blue
red
yellow
green
purple

输出样例:
red blue green yellow purple

#include<stdio.h>
#include<stdlib.h>
int main(void)
{
FILE * fp;
int i,m,j,k,d;
char ch[21][11];
int a[21],b[21];
if((fp=fopen("D:\\hnc.txt","a+"))==NULL){
   printf("File open error!\n");
     exit(0);
}//LHL'PTA 
for(i=j=0;;i++){ 
        j=0;
     for(;;j++){
        fscanf(fp,"%c",&ch[i][j]);
        printf("%c",ch[i][j]);
     	if(ch[i][j]=='\n'){
     	break;
     }
}
a[i]=j;
b[i]=i;
if(ch[i][j-1]=='#'){
	break;
  }
}
k=i;
for(i=0;i<k-1;i++){
	m=i;
	for(j=i+1;j<k;j++){
		if(a[m]>a[j]){
		m=j;
		}
	}
	j=a[m];
	d=b[m];
	b[m]=b[i];
	b[i]=d;
	a[m]=a[i];
	a[i]=j;
	}
 for(i=j=0;k>0;k--,i++){
   for(j=0;j<a[i];j++){
  	fprintf(fp,"%c",ch[b[i]][j]);
  	printf("%c",ch[b[i]][j]);
  }//LHL'PTA 
  fprintf(fp," ");
  printf(" ");
 }
 if(fclose(fp)){
    printf("Can not close the file!\n");
    exit(0);
 }
 return 0;

7-5 有理数加法 (10分)
本题要求编写程序,计算两个有理数的和。

输入格式:
输入在一行按照a1/b1 a2/b2的格式给出两个分数形式的有理数,其中分子和分母全是整形范围内的正整数。

输出格式:
在一行中按照a/b的格式输出两个有理数的和。注意必须是该有理数的最简分数形式,若分母为1,则只输出分子。

输入样例1:
1/3 1/6

输出样例1:
1/2

输入样例2:
4/3 2/3

输出样例2:
2

#include<stdio.h>

int gys(int a, int b){
    int t,c;
    if(a < b){
        t = b;
        b = a;
        a = t;
    }
    while(a != b){
            a = a - b;
            if(a < b){
            t = b;
            b = a;
            a = t;
        }
    }//LHL'PTA 
    return a;
}
int gcd(int a, int b){
    return a*b/gys(a,b);
}
int main(){
    int a1,b1, a2, b2;
    char q,w;
    while(scanf("%d %c %d %d %c %d" , &a1,&q, &b1, &a2 ,&w, &b2) == 6){
        int s = gys(b1, b2);
        int d = gcd(b1, b2);
        //b1 = d;
        //b2 = d;
        a1 = a1 * (d / b1);
        a2 = a2 * (d / b2);
        int sum = a1 + a2;
        int a = gys(sum, d);
        sum = sum/a;
        d = d/a;
        if(d == 1){
            printf("%d\n", sum);
        }
        else
            printf("%d/%d\n", sum, d);
    }//LHL'PTA 
    return 0;
}
1:求公约数的算法我用了辗转相减(因为思考量最少。。。),所以需要判断a,b的大小,然而如上的辗转相除(递归写法)就不需要,因为会自动调换过来
2:我用了求公约数再求公倍数,但是这是人算的时候比较方便,然而对于程序来说,直接将分母相乘要方便。
3:题中对于数的大小没有规定,但是学长们为了保险都用了long long
4:对于头文件以及一些简便的写法先写出来,这点值得借鉴



然而大神是这么写的

#include <cstdio>
#include <cmath>
#include <iostream>
#include <algorithm>
#include <vector>
#include <cstring>
#include <string>
#include <map>
#include <set>

using namespace std;
#define For(i,l,r) for(int (i)=(int)(l);(i)<(int)(r);++(i))
#define FOR(i,l,r) for(int (i)=(int)(l);(i)<=(int)(r);++(i))
#define rof(i,l,r) for(int (i)=(int)(l);(i)>=(int)(r);--(i))
typedef pair<int,int> pii;
typedef long long ll;
typedef unsigned long long llu;
typedef unsigned int ui;//LHL'PTA 

ll gcd(ll a,ll b){
    return b==0?a:gcd(b,a%b);
}

int main(){
 //   freopen("in.txt","r",stdin);
    ll a,b,c,d;
    scanf("%lld/%lld %lld/%lld",&a,&b,&c,&d);
    a=a*d+b*c;
    b*=d;
    ll g=gcd(a,b);
    printf("%lld",a/g);
    if(b/g!=1)printf("/%lld",b/g);
    puts("");

    return 0;
}

7-6 2017Final 圆周率山 (10分)
为了参加学校的社团风采展,怡山小学数学组的同学们决定画一座圆周率山,以宣传圆周率。

已知圆周率为:3.

1415926535 8979323846 2643383279 5028841971 6939937510

5820974944 5923078164 0628620899 8628034825 3421170679

8214808651 3282306647 0938446095 5058223172 5359408128

4811174502 8410270193 8521105559 6446229489 5493038196

输入格式:
输入山的高度,为一个不超过10的正整数。

输出格式:
以上尖下宽,左右对称的三角形形式,给出圆周率的前若干位(不含小数点)。注意:每行均以数字结尾,即数字右边无空格。

输入样例1:
1

输出样例1:
3

输入样例2:
4

输出样例2:
3
141
59265
3589793


#include <iostream>
using namespace std;
int main( )
{
    int n,sign;
    double total,f;
    n=1;
    total=0;
    sign=1;
    f=1; //用f代表待累加的每一项的绝对值
    while(f>1e-5)
    {
        total+=(sign*f);
        n+=2;
        f=1.0/n;
        sign*=-1; //sign变号
    }//LHL'PTA 
    cout<<"total="<<4*total<<endl;
    return 0;

7-7 通讯录排序 (10分)
输入n个朋友的信息,包括姓名、生日、电话号码,本题要求编写程序,按照年龄从大到小的顺序依次输出通讯录。题目保证所有人的生日均不相同。

输入格式:
输入第一行给出正整数n(<10)。随后n行,每行按照“姓名 生日 电话号码”的格式给出一位朋友的信息,其中“姓名”是长度不超过10的英文字母组成的字符串,“生日”是yyyymmdd格式的日期,“电话号码”是不超过17位的数字及+、-组成的字符串。

输出格式:
按照年龄从大到小输出朋友的信息,格式同输出。

输入样例:
3
zhang 19850403 13912345678
wang 19821020 +86-0571-88018448
qian 19840619 13609876543

输出样例:
wang 19821020 +86-0571-88018448
qian 19840619 13609876543
zhang 19850403 13912345678



//值得注意的是结构体间的交换,应该类型相同 
#include<stdio.h>
struct people{
	char name[10];
	int born;
	char number[20];	
}p[10],t;
int main(){
	int n,i,j;
	scanf("%d",&n);
	for(i=0;i<n;i++)
		scanf("%s %d %s",p[i].name,&p[i].born,p[i].number);
	for(i=0;i<n-1;i++)
		for(j=0;j<n-i-1;j++)	
			if(p[j].born>p[j+1].born){
				t=p[j];p[j]=p[j+1];p[j+1]=t;
			}
	for(i=0;i<n;i++)//LHL'PTA 
		printf("%s %d %s\n",p[i].name,p[i].born,p[i].number);
	return 0;
}

7-8 计算职工工资 (10分)
给定N个职员的信息,包括姓名、基本工资、浮动工资和支出,要求编写程序顺序输出每位职员的姓名和实发工资(实发工资=基本工资+浮动工资-支出)。

输入格式:
输入在一行中给出正整数N。随后N行,每行给出一位职员的信息,格式为“姓名 基本工资 浮动工资 支出”,中间以空格分隔。其中“姓名”为长度小于10的不包含空白字符的非空字符串,其他输入、输出保证在单精度范围内。

输出格式:
按照输入顺序,每行输出一位职员的姓名和实发工资,间隔一个空格,工资保留2位小数。

输入样例:
3
zhao 240 400 75
qian 360 120 50
zhou 560 150 80

输出样例:
zhao 565.00
qian 430.00
zhou 630.00

#include<stdio.h>
#include<iostream>
#include<math.h>
#include<string.h>
using namespace std;
struct gz
{
	char name[100];
	float jb;
	float fd;
	float zc;
	
}g[1000];

int main()
{
	int n,j,i,l,cnt=0;;
	cin>>n;//LHL'PTA 
	for(i=0;i<n;i++)
	{
		scanf("%s %f %f %f",g[i].name,&g[i].jb,&g[i].fd,&g[i].zc);
		printf("%s %.2f\n",g[i].name,g[i].jb+g[i].fd-g[i].zc);
		
	}
	
	return 0;
}


7-9 一帮一 (10分)
“一帮一学习小组”是中小学中常见的学习组织方式,老师把学习成绩靠前的学生跟学习成绩靠后的学生排在一组。本题就请你编写程序帮助老师自动完成这个分配工作,即在得到全班学生的排名后,在当前尚未分组的学生中,将名次最靠前的学生与名次最靠后的异性学生分为一组。

输入格式:
输入第一行给出正偶数N(≤50),即全班学生的人数。此后N行,按照名次从高到低的顺序给出每个学生的性别(0代表女生,1代表男生)和姓名(不超过8个英文字母的非空字符串),其间以1个空格分隔。这里保证本班男女比例是1:1,并且没有并列名次。

输出格式:
每行输出一组两个学生的姓名,其间以1个空格分隔。名次高的学生在前,名次低的学生在后。小组的输出顺序按照前面学生的名次从高到低排列。

输入样例:
8
0 Amy
1 Tom
1 Bill
0 Cindy
0 Maya
1 John
1 Jack
0 Linda

输出样例:
Amy Jack
Tom Linda
Bill Maya
Cindy John

#include <stdio.h>
#include <stdlib.h>

int main()
{
    int n;
    int i, j;
    int sex[50];
    char name[50][20];
    int arr[50] = {0};
//LHL'PTA 
    scanf("%d", &n);

    if(n < 0 || n > 50)
        exit(0);

    for(i = 0; i < n; i++)
    {
        scanf("%d", &sex[i]);
        scanf("%s", name[i]);
    }

    for(i = 0; i < n; i++)//从左边遍历
    {
        for(j = n-1; j >= 0; j--)//从右边找最靠右的、复合标准的人
        {
            if(arr[i] == 0 && arr[j] == 0 && sex[i] != sex[j])//找出符合条件的人,没被输出过,并且性别不同
            {
                printf("%s %s\n", name[i], name[j]);
                arr[i] = 1;
                arr[j] = 1;
            }
        }
    }

    return 0;
}
 

7-10 最大子列和问题 (10分)
给定K个整数组成的序列{ N
​1
​​ , N
​2
​​ , …, N
​K
​​ },“连续子列”被定义为{ N
​i
​​ , N
​i+1
​​ , …, N
​j
​​ },其中 1≤i≤j≤K。“最大子列和”则被定义为所有连续子列元素的和中最大者。例如给定序列{ -2, 11, -4, 13, -5, -2 },其连续子列{ 11, -4, 13 }有最大的和20。现要求你编写程序,计算给定整数序列的最大子列和。

本题旨在测试各种不同的算法在各种数据情况下的表现。各组测试数据特点如下:

数据1:与样例等价,测试基本正确性;
数据2:102个随机整数;
数据3:103个随机整数;
数据4:104个随机整数;
数据5:105个随机整数;
输入格式:
输入第1行给出正整数K (≤100000);第2行给出K个整数,其间以空格分隔。

输出格式:
在一行中输出最大子列和。如果序列中所有整数皆为负数,则输出0。

输入样例:
6
-2 11 -4 13 -5 -2

输出样例:
20

#include<iostream>
using namespace std;

int main(){
    int n;
    cin >> n;
    int num[n], j = 0, max = 0;
    for(int i = 0; i < n; i++){
        int x;
        cin >> x;
        if(x < 0)   num[j++] = x;
        else if (j > 0 && num[j-1] > 0)
        {
            num[j-1] += x;
        }else
        {
            num[j++] = x;
        }
        if(j > 2 && x > 0 && num[j-1] > -num[j-2]){
            num[j-3] = num[j-3] + num[j-2] + num[j-1];
            num[j-1] = num[j-2] = 0;
            j = j - 2;
        }//LHL'PTA 
        if(num[j-1] > max)  max = num[j-1];
    }
    cout << max;
    return 0;
}

发布了33 篇原创文章 · 获赞 14 · 访问量 615

猜你喜欢

转载自blog.csdn.net/Simple_questions/article/details/105063750
3.