源码在最后
1.内容要求
某班学生某学期学习了如下课程:高等数学(5学分)、C语言程序设计(3.5学分)、体育(2学分)、英语(3学分)、中国革命史(2学分),需对学生的考试成绩进行统计分析,编程实现如下功能:
(1)成绩的录入;
(2)根据考试成绩计算每位学生的总分、平均分、学分,每门课程考试合格(>=60分)则取得该门课程的学分,否则该门课程的学分为0;
(3)将平均分按照分数段进行统计;
(4)实现查找功能,例如输入某学生的学号,能够显示其所有信息;
(5)按学分进行排序;
(6)学分相同的情况下,总分高的在前,总分低的在后(选做)。
2. 设计思想
2.1程序框架
本程序以do while为框架(骨架),利用结构体、多个函数、和switch选择等(血肉)完成题目要求。
2.2思路阐述
1)选择do while为程序大框架
1. 与菜单(1.查看所有学生分数统计2.查看平均分分数段统计3.学生查找0.退出系统)保持一致
2. 可以利用do while实现功能的重复使用(多次查找学生,多次查看平均分分数段统计…)
3. 可以巧妙利用do…..while(0)的特点退出系统
2)多次利用函数
1. 降低复杂性:通过将大型问题分解为一系列较小的问题(每个函数解决一个小问题),简化编程任务,并且使主函数清晰明了,提高代码的可读性与可维护性
3)在do while中选择switch而不是if-else
1. 与一系列嵌套的if-else语句相比,switch语句可以更清晰地表示多种情况下的决策过程。
3. 系统实现
3.1 结构体
1)代码展示
2)代码解释:定义结构体
- 定义了一个名为
stu
的结构体类型,它包含了学生的姓名(name)、学号(id)以及五门课程的成绩(math、c、pe、eng、his)。其中,用long int类型存储学号。
3)代码解释:定义结构体数组
- 定义了一个大小为5的结构体数组 s,并初始化了每个数组元素。所有的成绩和学号都被初始化为0,所有姓名被初始化为字符 'a'。
3.2菜单函数
1)代码展示
2)代码解释
- 该函数负责学生考试成绩统计分析系统的菜单打印。
- 该函数的返回类型为void,参数也是 void。
3.3输入函数
1)代码展示
2)代码解释
- 该函数实现学生信息的输入。
- for循环5次以收集5名同学的考试信息,将收集到的信息存放在结构体数组中。
- 运用成员访问运算符来访问结构体数组s。
3.4学分计算函数
1)代码展示
2)代码解释
- 该函数实现学分计算
- 定义学分数组并初始化为0,该数组为全局数组。
- 该函数的返回类型为void,参数为int i,float m,float c,float pe,float eng,float his(学生序号和各科成绩)。
- 根据学分计算规则:每门课程考试合格(>=60分)则取得该门课程的学分,否则该门课程的学分为0。利用if判断,如果该门课程及格,则添加对应的学分到xuefen数组中。
3.4 平均分分数段统计函数
1)代码展示
- 代码解释
- 该函数实现平均分分数段统计
- 定义全局变量ABCDE,存储平均分各分数段的人数。
- 该函数的返回类型为void,参数类型为float。
- if-else实现分数段的确认,其中利用了逻辑与运算符 &&来确定分数范围,递增运算符 ++实现人数的增加。
3.5 main函数 (分段讲解)
- 代码展示1
2)代码解释1
- main函数的第一部分首先是欢迎,接着是input函数和menu函数实现学生信息录入和功能菜单打印。
- 定义平均分数组和input为后续准备
3)代码展示2
4)代码解释2
- 利用do while实现功能的重复使用(多次查找学生,多次查看平均分分数段统计…)
- switch实现功能的选择
- 巧妙利用do…..while(0)的特点退出系统
5)代码展示3:case 1
6)代码解释3: case 1
- case 1的作用是查看所有学生的分数统计。
- 首先利用for循环遍历所有的学生。
- 接着利用Xuefen函数计算该学生的分数。
- 最后打印该学生的信息、总分、平均分、学分。
7)代码展示4:case 2
8)代码解释4: case 2
- case2用于查看平均分分数段统计
- for循环遍历所有学生,计算平均分将其放入ave数组,然后利用分数段判断函数判断该分数段。
- 最后打印所有分数段的信息。
9)代码展示5:case 3
10)代码解释5: case 3
- case3用于学生查找。
- 首先定义长整型ids用于存放想要查找学生的学号。
- 接着for循环遍历所有学生,其中,利用if判断需查找学生的学号与当前循环到的学生的学号是否相同,如果相同,打印该学生的所有信息。
4. 总结
该程序实现了学生考试成绩统计分析系统,可以做到学生信息输入、查看所有学生的分数统计、查看平均分分数段统计、学生查找。符合设计要求。
在设计该系统的开始,我便决定使用do while为本程序的大框架,并利用switch与之配合。之后,难点便来到了细节的实现。为了将学生的许多信息存放在一起提高可读性,我利用了结构体数组存储学生信息。我还分别设计了菜单函数、输入函数、学分计算函数和平均分分数段统计函数以实现具体的功能,而且在每个函数中都综合利用了学习到的知识。
虽然我已经尽量使系统完美,但是该系统在实际应用中依然存在许多不足。比如:在某些地方(如计算平均分),存在多次执行相同的计算的情况;没有加入异常处理机制(检查用户输入的有效性,以防止非法输入导致问题);没有在程序中提供详细的错误提示等等…
下面为运行展示:
//C语言程序设计综合设计
//一、综合设计内容
// 如下课程:高等数学(5学分)、C语言程序设计(3.5学分)、体育(2学分)、英语(3学分)、中国革命史(2学分)
// 需对学生的考试成绩进行统计分析,编程实现如下功能:
//(1)成绩的录入;
//(2)根据考试成绩计算每位学生的总分、平均分、学分,每门课程考试合格( >= 60分)则取得该门课程的学分,否则该门课程的学分为0;
//(3)将平均分按照分数段进行统计;
//(4)实现查找功能,例如输入某学生的学号,能够显示其所有信息;
//(6)学分相同的情况下,总分高的在前,总分低的在后(选做)。
//二、要求
//(1)至少用函数实现一个或多个功能;
//(2)根据功能需求设计程序的结构;
//(3)以报告的形式上交作业打印版,内容主要包括如下部分:作业内容、功能模块设计、程序界面及代码、总结等内容
#include<stdio.h>
struct stu
{
char name[20]; //姓名
long long int id;//学号
float math; //高等数学
float c; //C语言程序设计
float pe; //体育
float eng; //英语
float his; //中国革命史
}s[5] = {
{'a',0,0,0,0,0,0,},
{'a',0,0,0,0,0,0,},
{'a',0,0,0,0,0,0,},
{'a',0,0,0,0,0,0,},
{'a',0,0,0,0,0,0,}
};
void menu()
{
printf(" 请选择功能\n");
printf("1.查看所有学生的分数统计\n");
printf("2.查看平均分分数段统计\n");
printf("3.查找学生\n");
printf("0.退出系统\n");
}
void Input()
{
printf("开始成绩录入\n");
printf("请依次输入学生姓名、学号、高等数学分数、C语言程序设计分数、体育分数、英语分数和中国革命史分数\n中间用空格隔开!\n");
for (int i = 0; i < 5; i++)
scanf("%s %lld %f %f %f %f %f", &s[i].name, &s[i].id, &s[i].math, &s[i].c, &s[i].pe, &s[i].eng, &s[i].his);
}
float xuefen[5] = { 0 };
void XueFen(int i,float m,float c,float pe,float eng,float his )
{
if (m >= 60)
xuefen[i] += 5;
if (c >= 60)
xuefen[i] += 3.5;
if (pe >= 60)
xuefen[i] += 2;
if (eng >= 60)
xuefen[i] += 3;
if (his >= 60)
xuefen[i] += 2;
}
int A = 0;
int B = 0;
int C = 0;
int D = 0;
int E = 0;
void ave_tongji(float a)
{
if (a >= 90 && a <= 100)
A++;
else if (a >= 80 && a < 90)
B++;
else if (a >= 70 && a < 80)
C++;
else if (a >= 60 && a < 70)
D++;
else
E++;
}
int main()
{
printf(" 欢迎来到学生考试成绩统计分析系统!\n");
Input();//成绩录入
printf(" 成绩录入成功!\n");
menu();//打印菜单
float ave[20] = { 0 };//平均分数组
int input = 0;
do
{
scanf("%d", &input);
switch (input)
{
case 1://查看所有学生的分数统计
for (int i = 0; i < 5; i++)
{
//计算学分
XueFen(i, s[i].math, s[i].c, s[i].pe, s[i].eng, s[i].his);
//打印学生的总分、平均分和学分
printf("%s(学号:%lld)的", s[i].name, s[i].id);
printf("总分为%f", s[i].math + s[i].c + s[i].pe + s[i].eng + s[i].his );
printf("平均分为%f", (s[i].math + s[i].c + s[i].pe + s[i].eng + s[i].his) / 5);
printf("学分为%f\n", xuefen[i]);
}
break;
case 2://查看平均分分数段统计
for (int i = 0; i < 5; i++)
{
ave[i] = (s[i].math + s[i].c + s[i].pe + s[i].eng + s[i].his) / 5;//计算平均分
ave_tongji(ave[i]);//分数段判断
}
printf("A(100-90)的人数为%d\n", A);
printf("B(90-80)的人数为%d\n", B);
printf("C(80-70)的人数为%d\n", C);
printf("D(70-60)的人数为%d\n", D);
printf("E(60-0)的人数为%d\n", E);
break;
case 3://学生查找
printf("请输入您想要查询的学生学号\n");
long long int ids;
scanf("%lld", &ids);
for (int i = 0; i < 5; i++)
{
if (ids == s[i].id)
{
printf("%s(学号:%lld)的信息如下:\n", s[i].name, s[i].id);
printf("高等数学分数为:%f\n", s[i].math);
printf("C语言程序设计分数为:%f\n", s[i].c);
printf("体育分数为:%f\n", s[i].pe);
printf("英语分数为:%f\n", s[i].eng);
printf("中国革命史分数为:%f\n", s[i].his);
printf("总分为%f ", s[i].math + s[i].c + s[i].pe + s[i].eng + s[i].his);
printf("平均分为%f ", (s[i].math + s[i].c + s[i].pe + s[i].eng + s[i].his) / 5);
printf("学分为%f \n", xuefen[i]);
}
}
break;
}
} while (input);
return 0;
}