当前位置:文档之家› 数据结构大作业实验报告

数据结构大作业实验报告

《数据结构》实验报告

--------------学生成绩分析系统

学校南京大学

院系工程管理学院

专业管理科学与工程类

年级 2010级

课题学生成绩分析系统

指导老师朱美琳

小组成员信息

姓名学号

叶皓恺101279055

殷承来101279056

于婴朴101279058

周道航101279062

摘要

一需求分析 (3)

二概要设计 (4)

一算法设计 (4)

二存储结构设计 (4)

三详细设计 (5)

四调试分析 (18)

一调试结果 (18)

二时间复杂度分析 (24)

三程序中存在问题以及可能改进的地方 (24)

五总结 (24)

一需求分析

本成绩分析管理系统可以实现以下主要功能:

1.信息的输入:建立学生档案文件(包括姓名,学号,班级,课程编号,成绩)

2.信息的维护:

添加:增加新学生

修改:学生信息的改变

删除:学生减少

3.信息的处理

按要求检索学生信息

按要求统计信息

本成绩分析管理系统同时可以实现以下系统界面:

1. 管理员进入

2. 一级菜单

输入“1”进入信息维护二级菜单

输入“2”进入信息检索二级菜单

输入“3”进入信息统计二级菜单

输入“4”退出系统

3. 二级菜单

信息维护

信息检索

信息统计

二概要设计

一算法设计

1. 用口令(密码)形式验证管理员身份(可输入三次密码),合法者进入,否则程序结束。算法实现可以使用break和continue语句,使用一个变量计数;

2. 有关功能说明

(1)建立学生成绩表void establish(void); //建立学生成绩表函数

建立新的学生纪录(包括姓名,学号,班级,课程编号,成绩)(暂定为2个班级,2门课程,学生个数每班10人左右)

算法实现可以使用fp头文件指针,将指定的记录写入相应的文本文件中;

(2)添加学生纪录void add(void); //添加学生纪录函数

在已存在的学生成绩文件中添加新纪录

算法实现同样利用文件操作将新添加的记录追加到文件的尾部即可;

(3)删除学生纪录void deleteinfo(void); //删除学生记录函数

在学生成绩文件中删除2个课程没有成绩的学生纪录

删除前,逐条显示符合删除条件的学生姓名,成绩,确认后再删除

算法实现先在文件中将记录读出,再寻找删除项,最后将其重新写入文本文件中;

(4)修改学生信息void modify(void); //修改学生记录函数

输入学生学号,在学生成绩文件中找出该学生纪录

在屏幕上逐条显示该学生的各条纪录

每显示一条,询问是否修改,如果“1",输入修改后的数据,文件原记录删除,保存新的记录

算法实现与删除学生记录相似就是将原文件内容读出,后根据条件修改内容,最后再重新写入文件中;判断是否修改时,利用if循环就可以了;

(5)按姓名和班级查找

输入姓名,显示该学生所有信息void searchname(void); //按姓名查找学生记录函数

输入班级,显示所有学生信息void searchclass(void); //按班级查找学生记录函数

算法实现先将文本内容读出,利用条件查找相应的记录,再将相应的记录输出

(6)信息统计void tongji(void); //统计学生成绩信息函数

同时按照班级和课程统计每门课程,每个课程每个班级的平均成绩,最高分,最低分

在屏幕上先依次显示各门课程,对应的各个班级的统计数据。

算法实现利用文件操作将学生成绩表中内容读出,然后利用循环语句将对应的统计项找到,输出结果

(7)退出信息管理系统,返回操作系统

利用switch case语句

二存储结构设计

因为每个学生纪录包括姓名,学号,班级,课程编号,成绩,所以要使用结构变量,同时考虑到处理数据的数量,我们采用结构数组来完成程序的实现,具体定义如下;

struct student{

char name[20]; //学生的姓名

long n; //学生的学号

char classnum[10]; //学生的班级

char coursenum[2][10]; //学生的所有课程编号

int grade[2]; //学生的各科的成绩

}STU[maxsize]; //最大数据容量常数maxsize

三详细设计

C语言源代码如下:

/*-----------------------------头文件定义-------------------------*/

#include

#include

#include

#include

/*-----------------------------------------------------------------*/

#define maxsize 20 //定义最大数据容量常数maxsize

/*----------数据类型定义-----------*/

struct student{

char name[20]; //学生的姓名

long n; //学生的学号

char classnum[10]; //学生的班级

char coursenum[2][10]; //学生的所有课程编号

int grade[2]; //学生的各科的成绩

}STU[maxsize];

/*---------------------------------*/

/*------------------------------函数列表----------------------*/

void establish(void); //建立学生成绩表函数

void add(void); //添加学生纪录函数

void deleteinfo(void); //删除学生记录函数

void modify(void); //修改学生记录函数

void searchname(void); //按姓名查找学生记录函数

void searchclass(void); //按班级查找学生记录函数

void tongji(void); //统计学生成绩信息函数

/*------------------------------------------------------------*/

/*=================---------主函数------------------------*/

int main(void)

{

int count,i,j;

char password[15]="1B620",password1[15]; //其中password为管理员密码;

printf("---------欢迎来到南京大学学生成绩分析系统--------\n");

/*-----------------管理员密码验证------------------*/

for(count=0;count<3;count++) //用密码形式验证管理员身份(可输入三次密码),合法者进入,否则程序结束

{

printf("----------请输入密码:------------\n");

gets(password1);

if(strcmp(password1,password)==0)

break;

else

continue;

}

/*------------------------------------------------*/

if(count==3)

return 0; //身份验证次数超过3次,程序结束;

else if(count<3)

{ /*----------------------一级菜单--------------------------*/

loop: //loop是回到一级菜单的语句标号

printf("-----------1 信息维护-----------\n");

printf("-----------2 信息检索-----------\n");

printf("-----------3 信息统计-----------\n");

printf("-----------4 退出---------------\n");

/*--------------------------------------------------------*/

scanf("%d",&i);

switch(i)

{

case 1:/*----------------------信息维护的二级菜单--------------------------*/

lo: //lo是回到信息维护二级菜单的语句标号

printf("-----------1 建立学生成绩文件-----------\n");

printf("-----------2 添加学生记录---------------\n");

printf("-----------3 删除学生记录---------------\n");

printf("-----------4 修改学生记录---------------\n");

printf("-----------5 返回上级菜单---------------\n");

/*--------------------------------------------------------*/

scanf("%d",&j);

switch(j)

{

case 1:establish();goto lo; //调用建立学生成绩表函数;并且调用完之后返回信息维护二级菜单

case 2:add();goto lo; //调用添加学生纪录函数;并且调用完之后返回信息维护二级菜单

case 3:deleteinfo();goto lo; //调用删除学生记录函数;并且调用完之后返回信息维护二级菜单

case 4:modify();goto lo; //调用修改学生记录函数;并且调用完之后返回信息维护二级菜单

case 5:goto loop; //回到一级菜单;

}

break;

case 2:/*-------------------------信息检索的二级菜单-------------------*/

op: //op是回到信息维护二级菜单的语句标号

printf("-----------1 按姓名查找-----------------\n");

printf("-----------2 按班级查找----------------\n");

printf("-----------3 放回上级菜单---------------\n");

/*-------------------------------------------------------------*/

scanf("%d",&j);

switch(j)

{

case 1:searchname();goto op; //调用按姓名查找学生记录函数;并且调用完之后返回信息检索二级菜单

case 2:searchclass();goto op; //调用按班级查找学生记录函数;并且调用完之后返回信息检索二级菜单

case 3:goto loop; //回到一级菜单

}

break;

case 3:/*----------------------------信息统计的二级菜单------------------------*/

to: //to是返回到信息统计的二级菜单的语句标号

printf("-----------1 成绩统计-----------------\n");

printf("-----------2 放回上级菜单----------------\n");

/*----------------------------------------------------------------------*/

scanf("%d",&j);

switch(j)

{

case 1:tongji();goto to; //调用信息统计函数;并且调用完之后返回信息统计二级菜单

case 2:goto loop; //回到一级菜单

}

break;

case 4: break;

}

}

return 0;

}

/*-------------------------------------------------------------------------*/

/*--------------------建立学生成绩文件函数的具体实现------------*/

void establish(void)

{

FILE *fp; //定义头文件指针fp;

int t,i;

printf("please input a number:"); //要输入的学生记录个数为t

scanf("%d",&t);

/*---------------------输入t条学生记录------------------------*/

for(i=0;i

{

scanf("%s%ld%s%s%s%d%d",STU[i].name,&STU[i].n,STU[i].classnum,STU[i].coursenum [0],STU[i].coursenum[1],&STU[i].grade[0],&STU[i].grade[1]);

}

/*--------------------------------------------------------*/

/*---------------打开成绩分析管理文本文件并添加学生记录---------------------*/

if( ( fp=fopen("成绩分析管理.txt","wb") )==NULL)

{

printf("打开文件错误\n");

return; //文件打开错误直接返回;

}

for(i=0;i

{

if(fwrite(&STU[i],sizeof(struct student),1,fp)!=1) /*写文件*/

{

printf("删除时写文件错误\n");

return;

}

}

fclose(fp);//关闭该文本文件;

/*---------------------------------------------------------------------------*/

return;

}

//-----------------------------------------------------------------

/*--------------------------------添加学生记录函数的具体实现-------------------*/

void add(void)

{

FILE *fp; //定义头文件指针fp

int cnt=0,i=0;

struct student *stu; //定义结构指针变量stu

printf("\nplease input the new student infomation!:");

if((stu=(struct student *)malloc(sizeof(struct student)))==NULL)

{ //为结构指针变量stu分

配存储空间

printf("\n分配存储空间错误!\n");

return ;

}

/*---------------为该结构变量赋值---------*/

scanf("%s%ld%s%s%s%d%d",stu->name,&stu->n,stu->classnum,stu->coursenum[0],stu->course num[1],&stu->grade[0],&stu->grade[1]);

/*--------------------将该结构变量加到成绩分析管理文本文件的末尾-------------*/

if(( fp=fopen("成绩分析管理.txt","ab") )==NULL) /*打开文件*/

{

printf("打开文件错误\n");

return;

}

if(fwrite(stu,sizeof(struct student),1,fp)!=1)/*写文件*/

{

printf("写文件错误\n");

return;

}

fclose(fp); /*--关闭文件----*/

/*---------------------------------------------------------------------------*/

return ;

}

/*---------------------------------------------------------------*/

/*-----------------------------删除记录函数的具体实现-------------*/

void deleteinfo(void)

{ FILE *fp; //定义头文件指针fp

int cnt=0,i=0,flag=0; //flag用作标识符,cnt和i用作计数

if((fp=fopen("成绩分析管理.txt","rb"))==NULL) /*打开文件*/

{

printf("打开成绩分析管理.txt文件失败\n");

return;

}

while(i

{

if(fread(&STU[i],sizeof(struct student),1,fp)==1) /*读文件*/

{

cnt++; //统计文件中记录条数

}

else

{

if(i==0)

printf("读文件失败\n");

break;

}

i++;

}

fclose(fp);/*关闭文件*/

/*-------------------------读取文件中的记录-------------------------*/

if((fp=fopen("成绩分析管理.txt","rb"))==NULL) /*打开文件*/

{

printf("删除时打开文件失败\n");

return;

}

for(i=0;i

if(fread(&STU[i],sizeof(struct student),1,fp)!=1) /*先读文件*/

{

printf("读文件错误\n");

return;

}

fclose(fp); /*关闭文件*/

/*------------------------------------------------------------------*/

for(i=0;i

if((STU[i].grade[0]==0)&&(STU[i].grade[1]==0))//输出各科成绩为0 的学生记录,并对学生的姓名做上标记;

{

printf("%s,%ld,%s,%s,%s,%d,%d\n",STU[i].name,STU[i].n,STU[i].classnum,STU[i].course num[0],STU[i].coursenum[1],STU[i].grade[0],STU[i].grade[1]);

strcpy(STU[i].name,"#"),flag=1;

}

if(!flag) printf("\nThere are no records to delete!\n ");//如果文件中没有满足条件的记录输出该信息

/*----------------------将删除后的学生记录写入文件中-------------------------------*/

if((fp=fopen("成绩分析管理.txt","wb"))==NULL) /*打开文件*/

{

printf("删除时打开文件失败\n");

return;

}

for(i=0;i

if( strcmp(STU[i].name,"#")!=0 )

if(fwrite(&STU[i],sizeof(struct student),1,fp)!=1) /*写文件*/

{

printf("删除时写文件错误\n");

return;

}

fclose(fp);/*关闭文件*/

/*--------------------------------------------------------------------------------*/

return ;

}

/*---------------------------------------------------------------------*/

/*------------------------------修改学生记录函数具体实现---------------------------*/

void modify(void)

{

FILE *fp; //定义头文件指针fp

long n1;

char name1[20];

char classnum1[10];

char coursenum1[2][10];

int grade1[2],ch,cnt=0,i=0,flag=1; //定义变量

/*---------------------打开成绩分析管理文本文件并读出文件中的学生记录-----------*/ if((fp=fopen("成绩分析管理.txt","rb"))==NULL) /*打开文件*/

{

printf("打开成绩分析管理.txt文件失败\n");

return;

}

while(i

{

if(fread(&STU[i],sizeof(struct student),1,fp)==1) /*读文件*/

{

cnt++;

}

else

{

if(i==0)

printf("读文件失败\n");

break;

}

i++;

}

fclose(fp);/*关闭文件*/

/*--------------------------------------------------------------------------------------*/

printf("\nplease input the student's number: ");

scanf("%ld",&n1); //输入要修改的学生记录的学号

for(i=0;i

if(STU[i].n==n1) //找到匹配的学生记录

{

/*-------------修改姓名的操作实现--------*/

printf("\n%s",STU[i].name); //输出原学生记录的姓名

printf("\nplease input 1 or 0!\n"); //判断是否改名,1代表改名,0代表不改

scanf("%d",&ch);

if(ch){

printf("Please input the new name:");

scanf("%s",name1); //输入新姓名;

strcpy(STU[i].name,name1),flag=0;//flag用作是否改动的判断标志}

/*--------------------------------------*/

/*--------------修改学号的操作实现---------*/

printf("\n%ld\nplease input 1 or 0!",STU[i].n);//输出原学生记录的学号并判断是否改学号,1代表改学号,0代表不改

scanf("%d",&ch);

if(ch){

printf("please input the new xuehao:");

scanf("%ld",&n1); //输入新学号

STU[i].n=n1,flag=0; //flag用作是否改动的判断标志

}

/*---------------------------------------*/

/*--------------修改班级的操作实现---------*/

printf("\n%s\nplease input 1 or 0!",STU[i].classnum);//输出原学生记录的班级并判断是否改班级,1代表改班级,0代表不改

scanf("%d",&ch);

if(ch){

printf("please input the new the classnum:");

scanf("%s",classnum1); //输入新班级

strcpy(STU[i].classnum,classnum1),flag=0;//flag用作是否改动的判断标志}

/*------------------------------------------*/

/*--------------修改课程名的操作实现---------*/

printf("\n%s\nplease input 1 or 0!",STU[i].coursenum[0]);//输出原学生记录的课程名并判断是否改课程名,1代表改课程名,0代表不改

scanf("%d",&ch);

if(ch){

printf("please input the new coursenum:");

scanf("%s",coursenum1[0]); //输入新课程名

strcpy(STU[i].coursenum[0],coursenum1[0]),flag=0;//flag用作是否改动的判断标志

}

printf("\n%s\nplease input 1 or 0!",STU[i].coursenum[1]);//输出原学生记录的课程名并判断是否改课程名,1代表改课程名,0代表不改

scanf("%d",&ch);

if(ch){

printf("please input the new coursenum:");

scanf("%s",coursenum1[1]); //输入新课程名

strcpy(STU[i].coursenum[1],coursenum1[1]),flag=0;//flag用作是否改动的判断标志

}

/*-------------------------------------------*/

/*--------------修改成绩的操作实现---------*/

printf("\n%d\nplease input 1 or 0!",STU[i].grade[0]); //输出原学生记录的成绩并判断是否改成绩,1代表改成绩,0代表不改

scanf("%d",&ch);

if(ch)

{

printf("please input the new grade1: ");

scanf("%d",grade1); //输入新成绩

STU[i].grade[0]=grade1[0],flag=0;

}

printf("\n%d\nplease input 1 or 0!",STU[i].grade[1]); //输出原学生记录的成绩并判断是否改成绩,1代表改成绩,0代表不改

scanf("%d",&ch);

if(ch){

printf("please input the new grade2: ");

scanf("%d",grade1+1); //输入新成绩

STU[i].grade[1]=grade1[1],flag=0; //flag用作是否改动的判断标志}

/*-------------------------------------------*/

}

if(flag)

printf("Can not find the data!"); //如果没有对应的学生记录的学号与已知的学号相匹配

/*-------------将修改好的学生记录重新写入学生成绩分析管理文本文件中----------*/

if((fp=fopen("成绩分析管理.txt","wb"))==NULL) /*打开文件*/

{

printf("修改时打开文件失败\n");

return;

}

for(i=0;i

if(fwrite(&STU[i],sizeof(struct student),1,fp)!=1) /*写文件*/

{

printf("删除时写文件错误\n");

return;

}

fclose(fp);/*关闭文件*/

/*---------------------------------------------------------------------------*/

return ;

/*-------------------------------------------------------------------*/

/*------------------------------按姓名查找学生记录函数的具体实现---------------------------*/

void searchname(void)

{

FILE *fp;//定义头文件指针fp

char s1[20];

int cnt=0,i=0,flag=1; //定义变量

/*---------------------打开成绩分析管理文本文件并读出文件中的学生记录-----------*/ if((fp=fopen("成绩分析管理.txt","rb"))==NULL) /*打开文件*/

{

printf("添加时打开成绩分析管理.txt文件失败\n");

return;

}

while(i

{

if(fread(&STU[i],sizeof(struct student),1,fp)==1) /*读文件*/

{

cnt++;

}

else

{

if(i==0)

printf("读文件失败\n");

break;

}

i++;

}

fclose(fp);/*关闭文件*/

/*-------------------------------------------------------------------------------------*/

printf("\n-------------please input the student's name:-------------------------\n");

scanf("%s",s1); //输入要查找的学生姓名

for(i=0;i

if(strcmp(STU[i].name,s1)==0) //找到匹配结果,输出匹配记录的内容并用flag做标记

flag=0,printf("%s,%ld,%s,%s,%s,%d,%d\n",STU[i].name,STU[i].n,STU[i].classnum,STU[i].cour senum[0],STU[i].coursenum[1],STU[i].grade[0],STU[i].grade[1]);

if(flag)

printf("There are no information to modify!\n"); //如果未找到匹配记录

return ;

}

/*--------------------------------------------------------------------------------------*/

/*-------------------------------按班级查找函数的具体实现--------------------------------*/

void searchclass(void)

{

FILE *fp; //定义头文件指针fp

char classnum2[10],flag=1;

int cnt=0,i=0; //定义变量

/*---------------------打开成绩分析管理文本文件并读出文件中的学生记录-----------*/

if((fp=fopen("成绩分析管理.txt","rb"))==NULL) /*打开文件*/

{

printf("添加时打开成绩分析管理.txt文件失败\n");

return;

}

while(i

{

if(fread(&STU[i],sizeof(struct student),1,fp)==1) /*读文件*/

{

cnt++;

}

else

{

if(i==0)

printf("读文件失败\n");

break;

}

i++;

}

fclose(fp);/*关闭文件*/

/*---------------------------------------------------------------------------------*/

printf("\nplease input a classname:");

scanf("%s",classnum2); //输入要查找的班级名称

for(i=0;i

if(strcmp(STU[i].classnum,classnum2)==0) //找到匹配结果,输出匹配记录的内容并用flag做标记

printf("%s,%ld,%s,%s,%s,%d,%d\n",STU[i].name,STU[i].n,STU[i].classnum,STU[i].course num[0],STU[i].coursenum[1],STU[i].grade[0],STU[i].grade[1]),flag=0;

if(flag)

printf("\nCan not find the infomation!\n"); //如果未找到匹配记录

return ;

}

/*-----------------------------------------------------------------------*/

/*-------------------------------信息统计函数的具体实现---------------------------*/

void tongji(void)

FILE *fp; //定义头文件指针fp

int

min1=101,min2=101,min3=101,min4=101,max1=0,max2=0,max3=0,max4=0,sum1=0,sum2=0,su m3=0,sum4=0,n1=0,n2=0,n3=0,n4=0,cnt=0,i=0;

float a,b,c,d;

char classnumber[2][10], coursenumber[2][10]; //定义变量

/*---------------------打开成绩分析管理文本文件并读出文件中的学生记录-----------*/

if((fp=fopen("成绩分析管理.txt","rb"))==NULL) /*打开文件*/

{

printf("打开成绩分析管理.txt文件失败\n");

return;

}

while(i

{

if(fread(&STU[i],sizeof(struct student),1,fp)==1) /*读文件*/

{

cnt++;

}

else

{

if(i==0)

printf("读文件失败\n");

break;

}

i++;

}

fclose(fp);/*关闭文件*/

/*-------------------------------------------------------------------------------*/

scanf("%s%s%s%s",classnumber[0],classnumber[1],coursenumber[0],coursenumber[1]); //输入要统计的班级和课程名称,各两个

for(i=0;i

{

if((strcmp(STU[i].classnum,classnumber[0])==0)&&(strcmp(STU[i].coursenum[0],coursenu mber[0])==0))

{

sum1+=STU[i].grade[0]; //求某门课班级的成绩总和

if(STU[i].grade[0]

min1=STU[i].grade[0]; //找求某门课班级的成绩最低值

if(STU[i].grade[0]>max1)

max1=STU[i].grade[0]; //找求某门课班级的成绩最高值

n1++; //计数

}

if((strcmp(STU[i].classnum,classnumber[0])==0)&&(strcmp(STU[i].coursenum[1],coursenumber [1])==0))

{

sum2+=STU[i].grade[1];//求某门课班级的成绩总和

if(STU[i].grade[1]

min2=STU[i].grade[1];//找求某门课班级的成绩最低值

if(STU[i].grade[1]>max2)

max2=STU[i].grade[1];//找求某门课班级的成绩最高值

n2++;//计数

}

if((strcmp(STU[i].classnum,classnumber[1])==0)&&(strcmp(STU[i].coursenum[0],coursenumber [0])==0))

{

sum3+=STU[i].grade[0];//求某门课班级的成绩总和

if(STU[i].grade[0]

min3=STU[i].grade[0];//找求某门课班级的成绩最低值

if(STU[i].grade[0]>max3)

max3=STU[i].grade[0];//找求某门课班级的成绩最高值

n3++;//计数

}

if((strcmp(STU[i].classnum,classnumber[1])==0)&&(strcmp(STU[i].coursenum[1],coursenumber [1])==0))

{

sum4+=STU[i].grade[1];//求某门课班级的成绩总和

if(STU[i].grade[0]

min4=STU[i].grade[1];//找求某门课班级的成绩最低值

if(STU[i].grade[1]>max4)

max4=STU[i].grade[1];//找求某门课班级的成绩最高值

n4++;//计数

}

}

a=(float)sum1/n1;//求某门课班级的平均成绩

b=(float)sum2/n2;//求某门课班级的平均成绩

c=(float)sum3/n3;//求某门课班级的平均成绩

d=(float)sum4/n4;//求某门课班级的平均成绩

/*---------------------------输出统计结果----------------------------*/

printf("\n%20s %20s %10.2f %10d %10d",classnumber[0],coursenumber[0],a,min1,max1); printf("\n%20s %20s %10.2f %10d %10d",classnumber[0],coursenumber[1],b,min2,max2); printf("\n%20s %20s %10.2f %10d %10d",classnumber[1],coursenumber[0],c,min3,max3); printf("\n%20s %20s %10.2f %10d %10d\n",classnumber[1],coursenumber[1],d,min4,max4);

}

/*------------------------------------------------------------------------------*/

四调试分析

一调试结果

1 身份验证界面

如果密码通过得到的界面如下:

如果密码输入三次未通过,得到以下界面:

选1就得到以下界面

选2就得到以下界面;

选3就得到以下界面;

选4就得到以下界面;

相关主题
文本预览
相关文档 最新文档