C语言实训报告之学籍管理系统.docx

上传人:b****5 文档编号:5028774 上传时间:2022-12-12 格式:DOCX 页数:43 大小:569.15KB
下载 相关 举报
C语言实训报告之学籍管理系统.docx_第1页
第1页 / 共43页
C语言实训报告之学籍管理系统.docx_第2页
第2页 / 共43页
C语言实训报告之学籍管理系统.docx_第3页
第3页 / 共43页
C语言实训报告之学籍管理系统.docx_第4页
第4页 / 共43页
C语言实训报告之学籍管理系统.docx_第5页
第5页 / 共43页
点击查看更多>>
下载资源
资源描述

C语言实训报告之学籍管理系统.docx

《C语言实训报告之学籍管理系统.docx》由会员分享,可在线阅读,更多相关《C语言实训报告之学籍管理系统.docx(43页珍藏版)》请在冰豆网上搜索。

C语言实训报告之学籍管理系统.docx

C语言实训报告之学籍管理系统

北京联合大学

实训报告

 

课程名称:

C语言程序设计课

项目名称:

学籍管理系统

学院:

自动化学院专业信息处理与智能技术

姓名:

杜旭亮陶晓申付娟

学号:

___________________________________________________

指导教师:

李论成绩:

2011年6月19日

一、实训题目与要求

1.问题提出

为了分析教学成果并进行相应的学籍处理,各学校每到期末都对综合成绩进行分类统计、上报成绩汇总结果等,这给每位教师和学籍管理人员带来很大的工作量。

使用学籍管理系统可以减少工作者的工作负担。

2.功能要求

循环显示如图(a)所示的主菜单。

请输入选项编号(0~4)请输入选项编号(0~4)请输入选项编号(0~4)

1-----录入成绩1---按学号排序1---生成并打印补考通知单

2-----统计成绩2---按平均分排序2—生成并打印退学名单

3-----处理学籍3—统计各分数段人数3—生成并打印新名单

4----创新功能4---返回4---返回

0----退出系统0---退出系统0----退出系统

(a)(b)(c)

在主菜单中选择1:

录入成绩。

假设某班的原始成绩单如下:

学号姓名高数英语编程电路法律

03zhanghe8992887997

13wangpei7286948377

23lifeng9184907983

其中,原始数据的排列时无序的。

系统应能够保留原始成绩单。

在主菜单选择2:

进入图(b)子菜单并统计成绩。

在此可以计算平均成绩,统计各分数段人数,按学号排序,按平均分排序。

在子菜单选择1时,将该班学生的成绩单按学号生序排列后存放在“按学号排序.txt.”文件中。

在子菜单选择2时,将该班学生的成绩单按平均分降序排序后存放在“按平均分排序.txt”文件中。

在子菜单选择3时,统计各分数段人数,并如表12.1所示的形式输出。

在子菜单选择4时,返回主菜单,选择0时,退出系统。

表12.1:

各门课、各分数段人数统计

90分以上

80~89分

70~79分

60~69分

60分以下

高数

英语

编程

电路

法律

在主菜单选择3:

进入如图(c)所示的子菜单,并处理学籍。

为不及格的同学打印补考通知单时,应在通知单上写明补考的科目,时间,地点(键盘输入)。

为了参加多门科目补考的学生,应避免时间重复。

为3门以上不及格的学生打印退学通知单,通知单上应打明学生的学号,姓名,退学原因(几门课不及格,成绩是多少)。

删除已退学的学生,将该班中升入高年级的学生信息写入文件“升学名单.txt”中。

在子菜单选择4,返回主菜单,选择0,退出系统。

在主菜单选择4,此功能学生自由发挥,根据本组爱好增加与本题目相关的新功能。

在主菜单选择0,显示结束信息,退出系统。

3.任务分工

组长:

杜旭亮。

负责小组程序的输入和创新部分,分配任务,使工作衔接有序。

将各部分文件衔接,查找错误,排版论文。

组员:

陶晓申

负责小组程序的处理学籍的部分。

主要负责绘制流程图,检查流程的连续,可操作性。

组员:

付娟

负责小组程序的成绩统计的部分。

完成自己部分的编程,流程图,组织论文的创作,主要负责论文部分。

二、设计实训题目功能

.总体设计

程序通过主模块调用其他函数来实现各种要求实现的功能。

显示主菜单模块通过调用myprint函数显示主菜单,提示使用的用户改执行的操作,实现基本的人机对话。

创建“学生基本信息.txt”文件由调用scoreInput函数通过键盘输入学生的信息。

统计学生信息调用函数scoreStat,并通过子菜单的选择实现功能。

处理学籍功能调用函数studentStatus,通过子菜单的选择实现处理学籍的功能。

创新功能由调用函数mynew,自己编写的新功能由这部分实现。

voidmainprint();/*主输出部分*/

voidscoreprint();/*成绩录入*/

voidscoreStat();/*统计成绩*/

voidstudentStatus();/*学籍处理*/

voidbukao();/*生成并打印补考通知单*/

voidtuixue();/*生成并打印退学通知单*/

voidxinmingdan();/*生成并打印新名单*/

voidsortAnhao();/*按学号排序*/

voidjisuanPingjun();/*计算平均分并排序*/

voidtongjiFenshu();/*统计分数段*/

voidfenxi();/*分析学生成绩,算出不及格门数*/\

voidmynew();/*创新功能*/

voidoutstudent();/*输出单个学生信息*/

voidoutdanke();/*输出单科成绩*/

voidteshutuixue();/*非考试退学*/

图2.1.1:

主模块图

 

(1)菜单的设计

①主函数的作用主要是调用myprint函数显示主界面,由于菜单比较简单所以采用printf函数将菜单项注意打印在屏幕上,边框则采用printf输出|-拼接起来实现人机对话的第一步.

②然后通过读取用户的输入,调用switch函数对用户的输入进行进一步的处理,并使用do-while函数实现用户的选择性的重复操作。

我们为用户提供了一个正常的出口,我们采用人机对话的形式,用户选择某一菜单以后,程序完成对于的功能,然后询问用户是否继续选择,用户即可退出也可以继续输入,而且主菜单0选项也可正常退出

图2.1.2总体设计流程图

算法设计

1,分析录入成绩模块算法:

创建一个文件“学生基本信息.txt”,并把从键盘输入的数据(学号、姓名、成绩)存放在该文件中;每写入一组记录,文件记录数增1。

建立录入成绩模块的流程图如下图所示。

采用先输入一组信息,应用scanf输入能有效阻止函数判断值的位置占用,采用while利用输入的信息都是非“#“,用“#”作为信息结束的判断语言。

如果没有输入“#”,则继续,并且i++。

图2.1.3:

输入流程图

2.分析成绩统计的算法:

成绩统计分为三大项和退出部分,按学号正向排序,按平均成绩逆向排序,打印各个分数段的人数。

利用switch方法使分支明确化。

2.1分析按学号排序模块的算法:

双重循环排序。

从学生基本信息.txt中读取信息,进行比较,假设第一个学生的学号是最小的,和之后的所有人进行比较,如果有比他学号还小的,将两个进行对调。

图2.2.1:

按学号排序流程图

2.2,按平均成绩排序:

先算每个人的平均成绩,存放,调用,双重循环排序;利用新定义的数组将成绩平均计算,依次排序,将学生成绩按平均成绩按降序排序。

2.3,统计各分数段人数并打印:

定义二维数组,将各科成绩转化成5个空间的成绩数组,双重循环,将各个成绩段的人数各次相加,得到最后结果;(如下图)

3.学籍处理:

此处分三部分和退出功能;打印补考学生名单;退学名单;升学名单;

3.1,打印补考学生名单:

由于不考需要考试场地,时间,而且互相不能重复,所以将考试科目,时间,地点都定义为二维字符串,方便输入和计算;补考学生要求是有一到三门科目不及格,所以要先判断,后计算是否补考;

图2.3.1:

生成并打印补考学生名单

补考的时间,地点都需要用键盘输入,在这儿我们采用了将科目名称字符串化,使其在对应的补考时间,地点能统一,时间地点的输入采用逐次输入,依次对比形势,如果发现有时间相冲突的补考科目,采用重新输入后一个补考科目时间地点的形式。

3.2,打印退学名单:

但不及格科目达到四门的时候,不参加补考,而是会被退学;由于升学名单和退学名单相互补充,所以我们在处理这方面时,采用先将文件读出,打印新名单时直接读出文件内容形式。

3.3,升学名单:

升学名单由非退学人员升入,故而此部分在退学名单中有所显示;打印新名单,将退学名单中的人删除,将后面的学生提前,覆盖原来学生的信息。

图2.3.3生成新名单

4.创新功能:

此部分为自由发挥部分,我们组的创新功能具有较强的针对性:

查询某学生信息;查询单科成绩;非考试不及格退学的学生;此部分依旧采用switch语言进入,选择具有多向性,显示更能清晰。

图2.4.0:

创新功能主流程图

4.1,查询学生信息:

此为学生查询部分。

输入自己的姓名就可以看到自己的情况;

图2.4.1:

查询单个学生成绩

4.2,查询单科成绩:

科目老师输入自己所教的科目,查考学生的情况;

图2.4.2:

查询单科成绩

4.3,非不及格退学学生:

因故不能继续上学的学生办理退学手续后班级清除其信息;

图2.4.3:

非考试原因退学学生

结构体说明

在程序中为了实现学生信息的链接统一,我们定义了结构体学生信息,通过结构体的调用实现信息的统一处理。

structstudent

{

charnum[13];/*学生学号*/

charname[18];/*学生姓名*/

floatmath;/*数学成绩*/

floatenglish;/*英语成绩*/

floatcprogram;/*c程序成绩*/

floatcircuit;/*电路设计成绩*/

floatlaw;/*法律基础成绩*/

floatpingjun;/*平均成绩*/

floatscore[5];/*定义五科成绩数组*/

};

程序代码设计

以补考函数为例讲解:

voidbukao()

{inti=0,j=0,count=0,n=0;chartime[5][10]={""},site[5][15]={""},sbj[5][10]={"高数","英语","c语言编程","电路设计","法律基础"};定义循环变量i,j并将其清零,定义参数常量count,n控制循环次数;定义二维字符串使输入的各科补考情况能进入循环。

structstudentex3[N]={0};定义结构体数组存放学生信息。

FILE*fp=NULL;定义文件指针指向文件。

system("color2f");给运行窗口加色。

fp=fopen("d:

\\学生基本信息.txt","r");打开之前输入的学生信息。

if(fp==NULL)

{printf("\n打开文件失败!

\n");return;}如果没有指向,则显示文件无法打开。

printf("\n欢迎进入生成并打印补考通知单系统!

\n");

while(feof(fp)==0)打开文件将文件中的内容读出。

{fscanf(fp,"%3d%15s%16s%f%f%f%f%f\n",&i,ex3[i].num,ex3[i].name,&ex3[i].score[0],&ex3[i].score[1],&ex3[i].score[2],&ex3[i].score[3],&ex3[i].score[4]);

i++;n++;}以数组形式读取文件便于循环。

fclose(fp);关闭文件。

for(i=0;i<5;i++)依次输入补考时间地点,循环比较,如果有冲突,重新输入。

{printf("\n请输入%s的补考时间、地点:

",sbj[i]);

scanf("%s%s",&time[j],&site[j]);

}

for(i=0;i<4;i++)

for(j=i+1;j<5;j++)

while(strcmp(time[i],time[j])==0&&strcmp(site[i],site[j])==0)

{printf("\n\n%s科目与%s科目相冲突,请重新输%s的考试时间、地点:

",sbj[i],sbj[j],sbj[j]);

scanf("%s%s",&time[j],&site[j]);

}

for(i=0;i

{for(j=0;j<5;j++)

if(ex3[i].score[j]<60){count++;

if(count>0&&count<3)符合补考条件,进入补考打印部分。

{printf("\n\n");

printf("\n%15s学生%d门课不及格,补考科目、时间、地点:

",ex3[i].name,count);

for(j=0;j<5;j++)

if(ex3[i].score[j]<60)

switch(j)定义二维字符串将科目数组化,使之循环。

找到对应科目,输出学生考试信息,补考信息。

{case0:

printf("\n高数:

%3.1f,时间%s,地点%s",ex3[i].score[j],time[j],site[j]);break;

case1:

printf("\n英语:

%3.1f,时间%s,地点%s",ex3[i].score[j],time[j],site[j]);break;

case2:

printf("\nc语言编程:

%3.1f,时间%s,地点%s",ex3[i].score[j],time[j],site[j]);break;

case3:

printf("\n电路设计:

%3.1f,时间%s,地点%s",ex3[i].score[j],time[j],site[j]);break;

case4:

printf("\n法律基础:

%3.1f,时间%s,地点%s",ex3[i].score[j],time[j],site[j]);break;

}

}}}

}程序结束。

此外,有几个特别的语言需要说明:

do

{mainprint();

printf("");

choose=getche();

switch(choose)

{

case'1':

scoreInput();break;/*成绩录入*/

case'2':

scoreStat();break;

case'3':

studentStatus();break;

case'4':

mynew();break;

case'0':

break;

default:

printf("\n%c是非法选项!

\n");break;

}

if(choose=='0')break;

printf("\n即将进入主菜单,要继续选择吗(Y/N)?

\n");

do

{

yes_no=getche();

}while(yes_no!

='Y'&&yes_no!

='y'&&yes_no!

='N'&&yes_no!

='n');

}while(yes_no=='y'||yes_no=='Y');

使用该语句来实现在用户输入选择项后,程序判断后进入对应模块,并相应的调用模块使用的函数进行运算,并使用break在调用完函数后退出switch语句。

然后询问用户是否继续操作,使用do-while语句来确认用户的输入的合法性,并使用使用getch语句来读取,然后使用外层的do-while判断是否退出循环;

而myprint函数简单使用了printf语句来显现将主菜单打印在屏幕上的功能。

for(i=0;i

for(j=i+1;j

if(strcmp(ex2[i].num,ex2[j].num)>0)

{temp=ex2[i];

ex2[i]=ex2[j];

ex2[j]=temp;

}

进行排序时,我们需要先将最开始的学生当成学号最小的学生,用后面的学习生的学号和他的进行对比,如果后面某个学生的学号筱宇第一个学生的学号,将这个学生的所有性能系和第一个学生对调,那么这个学生的信息就放在了第一位,如果后面还有这样的情况,将他们的位置对调。

循环完后面所有的学生后就确定了第一位的学生是学号最小的。

然后进行第二个排序,也是和后面的所有学生进行对比,有符合情况的,交换位置。

一次进行到倒数第二个,最后一个就不用比较了,他就是最大的。

而这部分的模式也是按平均分排序的主要模式。

for(j=0;j<5;j++)

for(i=0;i

{if(list[i][j]>100||list[i][j]<0)e++;

else{t=(int)list[i][j]/10;

switch(t)

{case10:

a[j][0]++;break;

case9:

a[j][0]++;break;

case8:

a[j][1]++;break;

case7:

a[j][2]++;break;

case6:

a[j][3]++;break;

default:

a[j][4]++;break;

}}

这部分是各科目各分数段人数统计,我们采用单科学生循环模式,a[j][]中j所代表的科目名称,我们只选取0~100分的人员进行操作,在实际输入的过程中可能会有输入的错误,我们将不在分数段的人不纳入统计范围,并且报错,除以10可以帮助我们选择相对应的分数段进行人数的相加。

for(i=0;i<5;i++)

{printf("\n请输入%s的补考时间、地点:

",sbj[i]);

scanf("%s%s",&time[j],&site[j]);

}

for(i=0;i<4;i++)

for(j=i+1;j<5;j++)

while(strcmp(time[i],time[j])==0&&strcmp(site[i],site[j])==0)

{printf("\n\n%s科目与%s科目相冲突,请重新输%s的考试时间、地点:

",sbj[i],sbj[j],sbj[j]);

scanf("%s%s",&time[j],&site[j]);

}

补考的考试时间和地点键盘输入,想将所有的补考信息输入,然后进行比较,依次使每一科的信息都和其他的相对比,选出时间相互冲突的,再次输入,直至所有的时间都不相冲。

printf("\n请输入要查学的学生的姓名:

");

scanf("%s",&ch);

for(i=0;i

if(strcmp(ex4[i].name,ch)==0)

{printf("\n您查询的是学号为%s的学生,他的成绩如下:

",ex4[i].num);

printf("\n高数:

%-7.1f,英语:

%-7.1f,c语言编程:

%-7.1f,电路设计:

%-7.1f,法律基础:

%-7.1f\n",ex4[i].score[0],ex4[i].score[1],ex4[i].score[2],ex4[i].score[3],ex4[i].score[4]);

break;}

if(i==n)printf("\n查无此人.......\n");

查询单个学生信息,输入学生的姓名,查找,如果有符合的学生,将他的信息输出且结束循环体,如果没有,即自动断出,那么查询所代表的i=n,这样,我们就判断出这个学生的信息不存在。

完整程序请参见附录A

测试与调试

测试数据类型

测试数据

预期结果

实测结果

合法数据

在主菜单中输入1

进入录入同学学籍菜单

进入录入同学学籍菜单

在创建同学学籍输入信息

在”d盘学生基本信息.txt”文件存入同学信息

d盘学生基本信息.txt文件有同学信息

非法数据

在主菜单中输入“a”

输出“a为非法选项”

输出“a为非法选项”

在每次完成一项是弹出“是否继续(Y/N)?

”输入y

没有反应

没有反应

图2.5.1开始状态

图2.5.2输入1之后

图2.5.3输入a之后

三.个人总结

杜旭亮的个人小结

两周的实训结束了,对于这次C语言实训,我非常重视,这次实训我们编辑的程序不再是简单的模块,而是具有一定应用性的学籍管理系统。

我们分到这个系统时认为这个系统程序调用函数少,可能是这次实训中最简单的,但是在实训开始后我们就发现,调用函数少,但是做的工作却是最多的。

没有过多的说明,没有这方面的经验,我们在刚开始的时候做的非常辛苦,第一,二天基本没有什么收获。

于是我们就进行严格的分工,将大片的信息处理成一个一个的模块。

在此次编程中,我负责的是开始的输入部分和最后的创新部分,这来那个部分都是比较简单的,但是如果用之前我的习惯,这段程序不仅繁杂而且可行性不高,我开始参考其他程序的输入部分,并找到了实用性较高的一个程序模板,并据此编写自己的程序。

在编辑运行方面,我发现好多知识的欠缺,最后我负责将程序汇总调整的时候,有许多程序语言需要翻书才能看明白,在调试环节我发现好多错误,有粗心导致的丢符号,有逻辑小问题,这都导致运行结果不符合要求,常常一整篇程序,就因为一个小小的错误而得不到实现,在不断的找寻错误解决错误的过程中,锻炼了我的耐心和毅力,更让我不懈坚持着。

在这里,我还要特别感谢我的指导老师,他总能在我对编程感到迷茫的时候鼓励我,让我不要着急,慢慢来,总会变好的。

每天他都在为学生们服务,非常辛苦,谢谢!

两周的实训就要结束了,这两周里,我学到了很多东西,c语言的实训室是束了,但我的学习不会结束,这次试训让我认识到了我们的生活中的很多东西都应用了程序,我将继续我的学习,编写有用的程序。

陶晓申的个人小结

在这两个星期里,我们在老师的带领下进行了C语言程序实践.在这之前我们已经对这门课程学习了一个学期.但是很多东西都只是停留在了解和书面的知识上.虽然老师会给我们很多的实践机会,.但像这次我们可以合作完成一个完整的程序还是第一次.我作为其中的参与者.感触颇多.

在这次的实训中,我对C语言有了一个更深的了解和认识,也对这个学期学到的知识得到了巩固.每次运行程序成功,拿下一个模块的时候,就很兴奋.让我对下面的编辑就更加充满了信心.通过合作,最终把最初学到的理论知识转化为基本技能.虽然只是很小的一个项目.但每天我们组都来的很早,大家一起学习.取长补短.我们很好的再实践中增长知识,提高我们的学习热情.尤其是在这次实训中,组长给了我很大的帮助.每次有问题他都会细心教我.让我弄明白了很多曾经不懂得东西.

在实训中,让我对C语言的热情进一步提高.而且让我深刻的认识到.很多时候,往往是细节决定成败,因为不管程序的语句是有多少,但只要是有一条语句或者语法不正确,就不能使程序得到所需要的结果

付娟的个人总结

为期两周的C语言的实训即将结束了,我们组制作的学籍管理系统也及时的完成。

对于这次C语言实训,我对此非常重视,因为通过实训不仅仅是对所学知识的验证,也是对团队合作,处理好同学关系的锻炼,为毕业后更好的融入社会做准备。

这两周的时间,我们

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 高等教育 > 军事

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1