资源描述
C语言程序设计
课程设计报告
设计题目:学生考勤系统设计
专 业 微电子科学与工程
班 级 微电 131
学 生 赵 杨 怡
指导教师
年 学期
设计任务:C语言课程设计任务书10
题目:学生考勤系统设计
功能:学生考勤系统应包含各班学生的所有信息。每个学生是一条记录,涉及姓名、性别、学号、日期、节次、出勤情况等信息。本系统可以模拟考勤过程、记录考勤结果,并能在课程结束后按照设定的考勤评分标准自动给出每个学生的考勤分数。
规定:1、用C语言实现程序设计;
2、运用结构体进行相关信息解决;
3、系统的各个功能模块规定用函数的形式实现;
4、界面和谐(良好的人机交互),程序加必要的注释。
平时成绩:
验收答辩成绩:
设计报告成绩:
总评成绩:
指导教师:
一、总体设计
1.程序的总体设计
◎拟定界面,使用户可选择操作项目(录入,修改,查询,评分)。
◎录入功能:使用结构体,规定用户输入姓名、性别、学号、日期、节次、当前出勤情况等信息,并写入文献。
◎修改功能:使用户输入学号,姓名其中一项可以修改考勤其信息。对于修改功能的实现,是先将所有文献内容读入到内存中,然后修改考勤值,最后再重新覆盖写入文献。
◎查询模块:使用字符串比较函数,运用循环找到相应结构体数组元素,然后输出需要信息。对于查询功能的实现,同修改,是先将所有文献内容读入到内存中,然后查找到其中某项,最后输出到屏幕。
◎评分模块:系统根据总的应道考勤数按照百分制,求出每个学生的分数,并输出到屏幕。
2. 数据结构
学生信息用结构体记录,涉及姓名(字符数组)、性别(字符型)、日期(年月日三个字符数组)、节次(整型)、出情况(整型)。
3. 函数原型声明
void main() //主函数
void input(); //录入数据函数
void change(); //修改数据函数
void search(); //查询数据函数
void evaluate(); //计算总评函数
二、具体设计
1.main( )函数
void main()
{
void input(); //录入数据函数
void change(); //修改数据函数
void search(); //查询数据函数
void evaluate(); //计算总评函数
char item;
system("color 34");
printf(" ★◇★□★◇★□★◇★□★◇★□★◇★□★\n");
printf(" ● ●\n");
printf(" ◇ 学 生 考 勤 管 理 系 统 ◇\n");
printf(" ● ●\n");
printf(" ◇ BY 朱胜佳 ◇\n");
printf(" ● ●\n");
printf(" ★◇★□★◇★□★◇★□★◇★□★◇★□★\n");
printf(" ● ●\n");
printf(" ◇ 1.学生信息及考勤情况录入 ◇\n");
printf(" ● ●\n");
printf(" ◇ 2.学生信息及考勤情况修改 ◇\n");
printf(" ● ●\n");
printf(" ◇ 3.学生信息及考勤情况查询 ◇\n");
printf(" ◎ ◎\n");
printf(" ● 4.学生考勤总评分数查询 ●\n");
printf(" ◇ ◇\n");
printf(" ★◇★□★◇★□★◇★□★◇★□★◇★□★\n"); //用户界面
printf("\n");
printf(" 请选择您需要的操作\n");
scanf("%c",&item);
switch(item)
{
case '1': input();break;
case '2': change();break;
case '3': search();break;
case '4': evaluate();break;
} //实现功能选择
}
流程图:
开 始
1
break
goal()
search()
amend()
record()
4
3
2
switch(item) switch(item)switch(item)
输出界面
结束
2. input() 函数
void input()
{
int i,j=0,jx=1;
printf(" ************************学 生 基 本 信 息 录 入*****************************\n");
if((fp=fopen("date.txt","w"))==NULL)
{
printf("文献打开失败\n");
exit(0);
}
for(i=0;jx==1;i++) //输入信息循环
{ for(;j==0;) //输入确认循环
{
getchar();
printf("请输入第%d个学生的姓名 ",i+1);
gets(stu[i].name);
printf("请输入第%d个学生的学号 ",i+1);
gets(stu[i].number);
printf("请输入第%d个学生的性别(男:m 女:f) ",i+1);
stu[i].sex=getchar();
printf("请输入第%d个学生的生日(格式:年 月 日) ",i+1);
scanf("%d%d%d",&stu[i].year,&stu[i].month,&stu[i].day);
printf("请输入第%d个学生的当前考勤次数 ",i+1);
scanf("%d",&stu[i].kq);
printf("您输入的信息为 姓名 %s 学号 %s 性别 %c 生日 %d年%d月%d日\n 0 重输 1 确认",stu[i].name,stu[i].number,stu[i].sex,stu[i].year,stu[i].month,stu[i].day);
scanf("%d",&j); //输入确认
}
j=0;
if(fwrite(&stu[i],sizeof(struct student),1,fp)!=1) printf("文献写入错误\n"); //写入文献
printf(" 是否继续输入下一个学生信息 0 终止 1 继续\n");
scanf("%d",&jx); //继续输入选择
}
fclose(fp);
printf("0 返回主菜单\n");
getchar();
a=getchar();
getchar();
if(a=='0') main(); //返回主菜单
}
流程图:
开始
0=>j
打开文献
1=>jx
0=>i
jx=1?
Y
j=0?
Y
输入i+1个学生信息生信息
N
输入j值选择是否确认
写入文献
i+1=>i
输入jx值选择是否继续
结束
3. change()函数
void change()
{ int i=0,j=0,sway,t,x;
char name[10],number[10];
printf(" **********************学 生 考 勤 修 改**************************\n");
if((fp=fopen("date.txt","r"))==NULL) //将文献内容读入内存
{
printf("文献打开失败\n");
exit(0);
}
for(i=0;feof(fp)==0;i++) fread(&stu[i],sizeof(struct student),1,fp); //读取文献内容
fclose(fp); //关闭文献
printf("选择查找方式 1 按照姓名查找 2 按照学号查找");
scanf("%d",&sway);
/**********************按照姓名查找开始*************************///
if(sway==1)
{
printf("请输入需要修改学生的姓名 ");
// printf("i=%d",i);
scanf("%s",name);
for(j=0;t!=0;j++)
{
t=strcmp(stu[j].name,name);
if(j==i)
{
t=0;
printf("未找到您所查询的数据,请重新输入\n");
}
}
if(j<i) //查询成功
{
printf("您查找的学生信息如下\n 姓名 %s 学号 %s 性别 %c 生日 %d年%d月%d日 当前考勤次数 %d\n",stu[j-1].name,stu[j-1].number,stu[j-1].sex,stu[j-1].year,stu[j-1].month,stu[j-1].day,stu[j-1].kq);
printf("是否修改该生考勤信息 0 否 1 是"); //选择是否修改考勤
scanf("%d",&x); //输入选择变量值
if(x==1)
{
printf("请输入新的考勤值 ");
scanf("%d",&stu[j-1].kq); //输入新的考勤值
if((fp=fopen("date.txt","w"))==NULL) //以只写方式打开文献
{
printf("文献打开失败\n");
exit(0);
}
for(j=0;j<i;j++) if(fwrite(&stu[j],sizeof(struct student),1,fp)!=1) printf("文献写入错误\n"); //写入文献
fclose(fp); //关闭文献
}
}
printf("是否继续修改其他学生考勤 0 否 1 是");
scanf("%d",&x);
if(x==1) change();
}
/**********************按照姓名查找结束*************************///
/**********************按照学号查找开始*************************///
if(sway==2)
{
printf("请输入需要修改学生的学号 ");
// printf("i=%d",i);
scanf("%s",number);
for(j=0;t!=0;j++)
{
t=strcmp(stu[j].number,number);
if(j==i)
{
t=0;
printf("未找到您所查询的数据,请重新输入\n");
}
}
if(j<i) //查询成功
{
printf("您查找的学生信息如下\n 姓名 %s 学号 %s 性别 %c 生日 %d年%d月%d日 当前考勤次数 %d\n",stu[j-1].name,stu[j-1].number,stu[j-1].sex,stu[j-1].year,stu[j-1].month,stu[j-1].day,stu[j-1].kq);
printf("是否修改该生考勤信息 0 否 1 是"); //选择是否修改考勤
scanf("%d",&x); //输入选择变量值
if(x==1)
{
printf("请输入新的考勤值 ");
scanf("%d",&stu[j-1].kq); //输入新的考勤值
if((fp=fopen("date.txt","w"))==NULL) //以只写方式打开文献
{
printf("文献打开失败\n");
exit(0);
}
for(j=0;j<i;j++) if(fwrite(&stu[j],sizeof(struct student),1,fp)!=1) printf("文献写入错误\n"); //写入文献
fclose(fp); //关闭文献
}
}
printf("是否继续修改其他学生考勤 0 否 1 是");
scanf("%d",&x);
if(x==1) change();
}
/**********************按照学号查找结束*************************///
printf("0 返回主菜单\n");
getchar();
a=getchar();
getchar();
if(a=='0') main();
}
开始
打开文献
将文献内容所有读入结构体数组
输入sway值选择查找方式
Sway=1?
N
Sway=2?
Y
输入要查找的学号
输入要查找的姓名
N
查找学号
查找姓名
输入X值选择是否修改考勤
X=1?
Y
输入新的考勤值
写入文献
结束
4. search()函数
void search()
{ int i=0,j=0,sway,t,x;
char name[10],number[10];
printf(" ***********************学 生 信 息 查 询***************************\n");
if((fp=fopen("date.txt","r"))==NULL) //将文献内容读入内存
{
printf("文献打开失败\n");
exit(0);
}
for(i=0;feof(fp)==0;i++) fread(&stu[i],sizeof(struct student),1,fp); //读取文献内容
fclose(fp); //关闭文献
printf("选择查找方式 1 按照姓名查找 2 按照学号查找");
scanf("%d",&sway);
/**********************按照姓名查找开始*************************///
if(sway==1)
{
printf("请输入需要修改学生的姓名 ");
// printf("i=%d",i);
scanf("%s",name);
for(j=0;t!=0;j++)
{
t=strcmp(stu[j].name,name);
if(j==i)
{
t=0;
printf("未找到您所查询的数据,请重新输入\n");
}
}
if(j<i) //查询成功
{
printf("您查找的学生信息如下\n 姓名 %s 学号 %s 性别 %c 生日 %d年%d月%d日 当前考勤次数 %d\n",stu[j-1].name,stu[j-1].number,stu[j-1].sex,stu[j-1].year,stu[j-1].month,stu[j-1].day,stu[j-1].kq);
}
printf("是否继续查询其他学生信息 0 否 1 是");
scanf("%d",&x);
if(x==1) search();
}
/**********************按照姓名查找结束*************************///
/**********************按照学号查找开始*************************///
if(sway==2)
{
printf("请输入需要修改学生的学号 ");
// printf("i=%d",i);
scanf("%s",number);
for(j=0;t!=0;j++)
{
t=strcmp(stu[j].number,number);
if(j==i)
{
t=0;
printf("未找到您所查询的数据,请重新输入\n");
}
}
if(j<i) //查询成功
{
printf("您查找的学生信息如下\n 姓名 %s 学号 %s 性别 %c 生日 %d年%d月%d日 当前考勤次数 %d\n",stu[j-1].name,stu[j-1].number,stu[j-1].sex,stu[j-1].year,stu[j-1].month,stu[j-1].day,stu[j-1].kq);
}
printf("是否继续查询其他学生信息 0 否 1 是");
scanf("%d",&x);
if(x==1) search();
}
/**********************按照学号查找结束*************************///
printf("0 返回主菜单\n");
getchar();
a=getchar();
getchar();
if(a=='0') main();
}
流程图:
开始
打开文献
将文献内容所有读入结构体数组
输入sway值选择查找方式
Sway=1?
N
Sway=2?
Y
输入要查找的学号
输入要查找的姓名
查找学号
查找姓名
输出该生信息
5. evaluate()函数
void evaluate()
{ int i=0,j=0,sway,t,x;
float score;
char name[10],number[10];
printf(" ***********************学 生 考 勤 分 数 计 算**************************\n");
if(kqcs==0)
{
printf("请输入应到考勤总数 "); //请输入应到考勤总数
scanf("%f",&kqcs);
}
if((fp=fopen("date.txt","r"))==NULL) //将文献内容读入内存
{
printf("文献打开失败\n");
exit(0);
}
for(i=0;feof(fp)==0;i++) fread(&stu[i],sizeof(struct student),1,fp); //读取文献内容
fclose(fp); //关闭文献
printf("选择查找方式 1 按照姓名查找 2 按照学号查找");
scanf("%d",&sway);
/**********************按照姓名查找开始*************************///
if(sway==1)
{
printf("请输入需要修改学生的姓名 ");
// printf("i=%d",i);
scanf("%s",name);
for(j=0;t!=0;j++)
{
t=strcmp(stu[j].name,name);
if(j==i)
{
t=0;
printf("未找到您所查询的数据,请重新输入\n");
}
}
if(j<i) //查询成功
{
printf("您查找的学生信息如下\n 姓名 %s 学号 %s 性别 %c 生日 %d年%d月%d日 当前考勤次数 %d\n",stu[j-1].name,stu[j-1].number,stu[j-1].sex,stu[j-1].year,stu[j-1].month,stu[j-1].day,stu[j-1].kq);
score=(stu[j-1].kq)/kqcs*100;
printf("该生当前考勤分数为 %5.2f",score);
}
printf("是否继续计算其他学生考勤分数 0 否 1 是");
scanf("%d",&x);
if(x==1) evaluate();
}
/**********************按照姓名查找结束*************************///
/**********************按照学号查找开始*************************///
if(sway==2)
{
printf("请输入需要修改学生的学号 ");
// printf("i=%d",i);
scanf("%s",number);
for(j=0;t!=0;j++)
{
t=strcmp(stu[j].number,number);
if(j==i)
{
t=0;
printf("未找到您所查询的数据,请重新输入\n");
}
}
if(j<i) //查询成功
{
printf("您查找的学生信息如下\n 姓名 %s 学号 %s 性别 %c 生日 %d年%d月%d日 当前考勤次数 %d\n",stu[j-1].name,stu[j-1].number,stu[j-1].sex,stu[j-1].year,stu[j-1].month,stu[j-1].day,stu[j-1].kq);
score=(stu[j-1].kq)/kqcs*100;
printf("该生当前考勤分数为 %5.2f",score);
}
printf("是否继续计算其他学生考勤分数 0 否 1 是");
scanf("%d",&x);
if(x==1) evaluate();
}
/**********************按照学号查找结束*************************///
printf("0 返回主菜单\n");
getchar();
a=getchar();
getchar();
if(a=='0') main();
}
流程图:
开始
输入应到考勤次数kqcs值
打开文献
将文献内容所有读入结构体数组
输入sway值选择查找方式
Sway=1?
Y
N
Sway=2?
输入要查找的学号
输入要查找的姓名
查找学号
查找姓名
输出该生信息
计算考勤分数
输出考勤分数
结束
三、测试及调试(测试方案、存在的问题及解决方法)
测试方案:按照每个函数功能进行测试,在做完每个函数对其进行测试,主函数测试,先将所有需要的功能模块函数设立为空,每个函数用一个printf语句来测试主函数。
1. 存在问题:开始将生日定义为字符数组,当用scanf来输入年月日时,年月日之间用空格分隔,但在输出时发现年月日出现错误。
分析因素:用scanf输入年月日时,系统会把用来分隔的空格当做字符读入。
解决方法:将年月日定义为整型,这样就可以用scanf输入,用空格隔开。
2. 存在问题2:在查找数据时,需要先将所有数据读入一个结构体数组,在读取后未关闭文献,执行查找时查找不到相关信息。
分析因素:再运用for循环读取所有文献内容后,文献指针将会移至文献末尾,这样再执行查找时就会从文献末尾开始,显然不符合规定,所以会出现错误。
解决方法:在读取完数据后先关闭文献,在查找时再次打开文献,这时文献指针就会指向文献开头。
3. 存在问题3:再多个使用getchar或者gets输入的时候,会出现直接跳过输入的情况。
分析因素:在使用getchar或者gets输入的时候,系统会将前一步用来确认执行的回车当成字符读入,导致跳过该步输入。
解决方法:再getchar或者gets前面加上getchar()语句,读掉回车,下面的getchar或者gets就可以正常输入。
四、小结
通过编写该程序,熟悉了C语言的基本语法,选择,循环等结构,进一步练习了函数的调用方法,和文献的读写方法,熟悉了结构体的使用,更加深化了面向过程语言思想,和一些基本算法。
通过对程序的后期调试,熟悉了C常见错误,锻炼了思维的严密性,和完备性。
通过对程序的注释和画流程图,形成了一套自己编程的风格,和清楚地思绪,使思维更加条理化,清楚化。
附件:重要源程序代码(需打印)
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
FILE *fp; //定义文献
char a; //返回选择变量
float kqcs=0; //应到考勤次数变量
struct student
{ char name[10];
char number[11];
char sex;
int year;
int month;
int day;
int kq;
}stu[100]; //定义储存学生信息的结构体数组
//********************************************主 函 数 开 始************************************************
void main()
{
void input(); //录入数据函数
void change(); //修改数据函数
void search(); //查询数据函数
void evaluate(); //计算总评函数
char item;
system("color 34");
printf(" ★◇★□★◇★□★◇★□★◇★□★◇★□★\n");
printf(" ● ●\n");
printf(" ◇ 学 生 考 勤 管 理 系 统 ◇\n");
printf(" ● ●\n");
printf(" ◇ BY 朱胜佳 ◇\n");
printf(" ● ●\n");
printf(" ★◇★□★◇★□★◇★□★◇★□★◇★□★\n");
printf(" ● ●\n");
printf(" ◇ 1.学生信息及考勤情况录入 ◇\n");
printf(" ● ●\n");
printf(" ◇ 2.学生信息及考勤情况修改 ◇\n");
printf(" ● ●\n");
printf(" ◇ 3.学生信息及考勤情况查询 ◇\n");
printf(" ◎ ◎\n");
printf(" ● 4.学生考勤总评分数查询 ●\n");
printf(" ◇ ◇\n");
printf(" ★◇★□★◇★□★◇★□★◇★□★◇★□★\n"); //用户界面
printf("\n");
printf(" 请选择您需要的操作\n");
scanf("%c",&item);
switch(item)
{
case '1': input();break;
case '2': change();break;
case '3': search();break;
case '4': evaluate();break;
} //实现功能选择
}
//**************************************************主 函 数 结 束**************************************************
///*****************************************录入数据函数内容开始***********************************************************
void record()
{
int i,j=0,jx=1;
printf(" ************************学 生 基 本 信 息 录 入*****************************\n");
if((fp=fopen("date.txt","w"))==NULL)
{
printf("文献打开失败\n");
exit(0);
}
fo
展开阅读全文