1、 应用技术学院 课 程 设 计 报 告 课程设计 C语言课程设计 课题名称 班级档案管理系统 专 业 电气工程及其自动化 班 级 0783 学 号 200713010332 姓 名 黎硕玮 指导老师 王颖
2、 2008年3月22日 课程设计任务书 课程名称 C语言程序设计 课题名称 班级档案管理系统 专业班级 电气0783班 学生姓名 黎硕玮 学 号 200713010332 指导老师 王颖 审 批 任务书下达日期:2008 年3月15日 任务完成日期
3、2008年3月22日 《C语言课程设计》任务书 前言 《C语言程个序设计》课程设计是对学生的一种全面综合训练,它包括问题分析,总体结构设计,用户界面设计,程序设计基础技能和技巧,多人合作,以致一整套软件工作规范的训练和科学作风的培养。是与课堂听讲、自学和联系相辅相成的必不可少的一个教学环节。通常,课程设计的课题比平时的习题复杂得多,也更接近实际。课程设计着眼于理论与应用的结合点,使学生学会如何把书上学到的知识用于解决实际问题,培养程序设计工作所需要的知识综合能力;另一方面,能使书上的知识变“活”,使学生更好地深化理解和灵活掌握教学内容。为了达到上述目的,本课程设计安排了十五个设计课
4、题,训练重点在于基本的程序设计方法和分析问题的能力,而不强调面面俱到。学生选其中一题进行设计,设计完毕写出课程设计报告,用A4纸打印成册;并将课程设计报告与源程序存盘。学习委员将课程设计报告与磁盘(缺一不可)收齐以后交指导老师。 一、目的 全面熟悉、掌握C语言基本知识,掌握C语言程序设计中的顺序、分支、循环三种结构及数函数和C语言基本图形编程等方法,把编程和实际结合起来,增强对不同的问题运用和灵活选择合适的数据结构以及算法描述的本领,熟悉编制和调试程序的技巧,掌握分析结果的若干有效方法,进一步提高上机动手能力,培养使用计算机解决实际问题的能力,养成提供文档资料的习惯和规范编程的思想,为以后
5、再在专业课程中应用计算机系统解决计算、分析、实验和设计等等学习环节打下较扎实的基础。 二、基本情况 课程类别:必修课 课程学分:1学分 课程学时:一周 课程对象:电气工程0781、0782、0783、0784、0785、0786 三、时间安排 时间 任务 2008-3-8下午3:40-5:40 指导老师给学生布置课程设计的任务及要求 2008-3-10到2008-3-15 学生根据设计任务及要求,对系统进行需求分析、概要设计和详细设计,并在此基础上编写程序代码 学生提交系统程序清单初稿 上机调试程序 修改并完善程序并上机调试程序 20
6、08-3-16 接受指导老师的验收 2008-3-16到2008-3-22 书写课程设计报告 提交课程设计报告 四、设计可调试过程规范化要求 1) 需要分析 分析系统功能需求以及用户操作流程。 2) 概要设计 在需要分析的基础上,确定系统总体框架(系统功能结构图) 3) 详细设计 定义数据储存结构,并设计实现系统功能的具体算法,画出各算法的工作流程图。 4) 代码设计 根据所设计的算法,定义相应函数分别实现系统的各子功能模块,同时由主程序提供友好的用户界面,使用户可通过选择主菜单来调用课程设计中要求完成的各个功能模块,子程序执行完后还可以返回主菜单,继续选择其他功
7、能执行。源程序要求书写规范,结构清晰。重点函数的重点变量。重点功能部分均要求给出清晰的程序注释 5) 程序调试 程序编译、连接成功后,自己设计实现程序功能的一组或多组测试数据,并严格按照此测试数据进行测试,然后分析测试结果。如果程序不能正常运行或结果不正确,则需要对程序进行单步调试,在进行过程中认真查找算法实现中存在的问题,并加以分析和改正。如果程序能够基本正确运行,可考虑增加若干基本的容错功能(如避免用户操作错误时程序出现死循环等);另外尽量对现有算法给出改进方案,并比较不同算法之间的优缺点。 五、设计报告及书写内容要求 课程设计任务完成后,每位同学必须独立书写一份课程设计报告,
8、注意:不得抄袭他人的报告(或给他人抄袭),一旦发现,成绩为零分。课程设计报告的内容应包括以下五个部分: 1) 需求分析:包括设计题目、设计要求以及系统功能需求分析; 2) 概要设计:包括系统总体设计框架和系统功能模块图; 3) 详细设计:包括主要功能模块的算法设计思路以及对应的工作流程图; 4) 主要源程序代码:包括存储结构设计说明,以及完整源程序清单; 5) 调试分析过程描述:包括测试数据、测试输出结果,以及对程序调试过程中存在的问题的思考(列出主要问题的的出错想象、出错原因、解决方法及效果等); 6) 总结:包括课程设计过程中的学习体会与收获,对C语言和本次课程设计的认识以及自
9、己的建议等内容。 7) 书写格式严格按所附要求书写。 附:课程设计报告装订顺序:封面、任务书、目录、正文、评分、附件(A4大小的图纸及程序清单)。 正文格式:一级标题用3号黑体,二级标题用四号宋体加粗,正文用小四号宋体,行距22 。 正文内容:一、课题的主要功能;二、课题的功能模块可划分(要求画出模块图);三、主要功能的实现(至少要有一个主要模块的流程图);四、程序调试;五、总结;六、附件(所有程序的原代码,要求对程序写出必要的注释)。 正文总字数要求在5000字以上(不含程序源代码)。 六、考核方式 指导老师负责验收程序的运行结果,并结合学生的工作态度、实际动手能力、创新精神和
10、设计报告等进行综合考评,并按优秀、良好、中等、及格可不及格五个等级给出每位同学的课程设计成绩。具体考核标准包含以下几个部分: 1) 平时出勤(占10%) 2) 系统需求分析、功能设计、数据结构设计及程序总体结构合理与否(占10%) 3) 程序能否完整、准确地运行,个人能否独立、熟练地调试程序(占40%) 4) 设计报告(占30%) 5) 独立完成情况(占10%) 七、指导老师 王颖 八、课程设计题目 1.问题描述: 对一个有N个学生的班级,通过该系统实现对该班级学生的基本信息进行录入、显示、修改、删除等操作的管理。课题二:班级档案管理系统的设计与实现。 2.功能要求:
11、1)本系统采用一个包含N个数据的结构体数组,每个数据的结构应当包括:姓名、学号、性别、年龄、备注。 (2)本系统显示这样的菜单: 班级档案管理系统 请选择系统功能项: a.学生基本信息录入 b.学生基本信息显示 c.学生基本信息存储 d.学生基本信息删除 e.学生基本信息修改(修改前要求输入密码) f.学生基本信息查询 ①按姓名查询 ②按学号查询 g. 退出系统 (3)执行一个具体的功能之后,程序将重新显示菜单。 3.算法提示: (1)数据结构:结构体类型数组。 (2)数据库结构:该系统的基本数据库如下: 4.测试数据: 姓名 学号
12、性别 年龄 备注 char char char int char 学生人数N=10 5.对该系统有兴趣的同学可以在实现上述基本功能后,完善系统的其它功能。 目录 课程设计主文档 9 一、课程设计题目 9 二、内容摘要 9 三、关键字 9 四、总体设计方案的选定 9 【概要设计】 9 【详细设计】 10 五、函数细说 10 六、函数间的调用关系图 14 七、主控模块和部分子模块 18 八、附件 19 九、调试分析 29 十、总结 30 十一、参考资料 30 应用
13、技术学院课程设计评分表 31 课程设计主文档 一、课程设计题目 班级档案管理系统 二、内容摘要 该系统是一个简单的班级档案管理系统,能够使学生了解到相应的信息。同时也减少了老师的工作量。整个系统除了主函数外,另外还有12个函数,实现8大功能:输入信息功能、显示信息功能、查询信息功能、插入信息功能、保存信息功能、读取信息功能等。 三、关键字 档案管理系统 函数 数组 结构体 文件 循环语句 多分支结构 四、总体设计方案的选定 程序的功能:要实现对班级学生档案的统一有效的管理,就需要通过运用函数,编译语句,数据类型来实现,由于班
14、级中学生信息数据多,数据结构相似的特点,很明显自然的想到用数组实现数据的存储,且总体数据结构应用文件类型的数据,文件类型为结构体数据,数据库结构用文件来实现,需要存储的信息数据有:学生的姓名,学号,性别,年龄等。最后通过函数之间的调用来实现。 【概要设计】 程序的模块组成以及各个函数的功能: 1)、 程序的模块组成: 主函数: int main() 输入函数: STUDENT *create() 显示函数: void print(STUDENT *head) 查询函数: void search(STUDENT *head
15、) 删除函数: STUDENT *delete(STUDENT *head) 插入函数: STUDENT *insert(STUDENT *head,STUDENT *new) 保存函数: void save(STUDENT *head) 2)、 各个函数的主要功能: 输入函数: 随时输入数据。 显示函数: 显示各个函数和数据。 寻找函数: 方便学生查找自己的信息。 删除函数: 方便工作人员修改学生信息。 插入函数: 可以插入新的信息。 保存函数:
16、 保存好学生信息,以免丢失 【详细设计】 相关的数据类型: 班级档案结构数组 typedef struct z1 { /*定义数据结构*/ char no[12]; char name[15]; char sex[N]; int age; char remark stru
17、ct z1 *next; } 五、函数细说 整个系统除了主函数外,另外还有12个函数,实现八大功能:输入功能、显示功能、查找功能、插入功能、保存功能、读取功能。各个函数的详细设计说明分别如下: 1.主函数 main() 利用无限次循环for(;;)和swithch()实现各函数的调用,系统根据输入的数字选项来调用相应的函数。 2. 菜单选择函数 int menu_select() 个这是一个无参函数,主要实现“功能选择”的界面,在这个界面里有显示系统的八大功能,根据每功能前面的序号进行选择,中间还显示系统当前的时间。等执行完每一个函
18、数功能后,按任一键回到主界面也要通过这个函数来实现! 3.输入记录函数 STUDENT *create() 这是一个无参函数,用来执行第学生基本信息的输入,当学生学号为@时停止输入,函数结束后,带回一个指向链表头的指针head。 算法:先声明一个首节点head,并将head->next设为NULL。每输入一个数据就声明一个新节点p,把p->next设为NULL,并且链接到之前列表的尾端。 N-S流程图如下: head=NULL for(i=0;i<=2;i++) 否 是 指针p指向新开辟的单元 指针p是否为空 输入学号p->no 输
19、出内存溢出 p->no是否为@ 否 是 停止输入返回 输入姓名p->name 输入年龄p->age 输入性别p->sex 输入备注p->remark 菜单 p->next=head;head=p; 4.显示记录函数 void print(STUDENT *head) 这是一个不返回值的有参函数,形参为“链表头的指针”,负责对全部学生成绩记录的输出,不足之处就是不能对学生成绩进行分页显示。 算法:先将p结点的指针指向第一个结点,将p结点(即第一个结点)的数据输出。然后再将p结点的指针指向p指针的的指针(即下一结点),将p结点(即第一结点)
20、的数据输出。重复执行此步聚直到p指针指向NULL为止。 N-S流程图如下: p=head,使指向第一个结点 输出p所指向的结点 p指向一下个结点 当p指的不是表尾 5.查找记录函数 void search(STUDENT *head) 这是一个不返回值的有参函数,形参为“链表头的指针”,实现按姓名对某个学生进行查找,并显示所查找到的记录。 算法:采用线性查找法往下一个节点查找。输入所要查找的学生的姓名s,设一个指针变量p,先指向第一个结点,当strcmp(p->name,s) && p != NULL时,使p后移一个结点,如果p!=NULL
21、输出p所指的结点。 N-S流程图如下: 输入要查找的学生的姓名s p=head,使p指向第一结点 当记录的姓名不是要找的,或指针不为空时 p=p->next p!=NULL如果指针不为空 是 否 输出p所指向的结点 显示没有该学生 6.删除记录函数 STUDENT *delete(STUDENT *head) 这是一个有参函数,形参为“链表头的指针”,先通过密码程序,即输入一个无回显示的字符串a[],如果输入的字符串与系统设定的字符串pass相同,就可以进入删除函数,否则返回菜单。进入删除函数后,输入要删除的学生记录的姓名,找到后显示该学生信息,等确认后便
22、可按回车进行删除。 算法:从p指向的第一个结点开始,检查该结点中的num值是否等于输入的要求删除的那个姓名。如果相等就将该结点删除,如不相等,就将p后移一个结点,再如此进行下去,直到遇到表尾为止。 N-S流程图如下: 输入一个字符串a[] If (a! =pass) Else continue Return h p1=head; 当(strcmp(p1->no,s))&& p1 != NULL p2=p1 p1=p1->next 否 p1是要删除的结点 是 p1所指是头结点 输出找不到的信息 否 p2->next=p1-next
23、
head=p1->next (删除头结点)
是
7.插入函数 STUDENT *insert(STUDENT *head)
这是一个有参函数,形参有两个,一个是“链表头的指针”,一个是“待插入指针”,按照学号进行插入,并返回。
算法:先用指针变量p指向待插入的结点,q指向第一个结点。如果p->no
24、将p0所指的结点插到链表末尾。如果插入的位置既不在第一个结点之前,又不在表尾结点之后,则将p的值赋给info->,使info->next指向待插入的结点,然后将q的值赋给p->next,使得p->next指向q指向的变量。如果插入位置为第一个结点之前,则将p赋给head,将q赋给p->next。如果要插到表尾之后,应将p赋给q->next,NULL赋给p->next。
N-S流程图如下:
q=head, p=new
原来的链表是空表
是
否
当P0所指的结点作为唯一结点
当p->no
25、o>=p->no head=p, p->next=q(插到表头之前) info->next=p, p->next=q(插到表中间) q->next=p p->next=NULL (插到表尾之后) q指向头结点 否 否 是 是 8.保存数据到文件函数 void save(STUDENT *head) 这是一个不返回值的有参函数,形参为“链表头的指针”,可以把学生记录保存在电脑上由自己任意命名的二进制文件。 输入要保存记录的文件地址outfile N-S流程图如下: 否 是 p=head
26、 当p不为空时 息,并返回菜单文件不能打开 fwrite(p,LEN,1,fp); (写入一条记录) p=p—>next; (指针后移) 输出一个出错信息,并返回菜单 fclose(fp); (关闭文件) 9.从文件读数据函数 STUDENT *load() 这是一个不返回值的有参函数,形参为“链表头的指针”,根据输入的文件地址进行读取。 N-S流程图如下: 定义两个指针变量p1,p2 输入要打开的记录文件地址infile 文件不能打开 否 是 开辟一个新单元 指针p1是否为空 返回菜单 否 是 返回菜单 读入记录
27、fclose(fp); (关闭文件) 六、函数间的调用关系图 1 main 函数的下属子功能函数及其调用示意图 main() insert() exit() save() create() delete() print() search() load() menu_select() 2 统计函数的下属功能函数及其调用示意图 getch() gotoxy() cprintf() menu_select() textcolor pu
28、tch() window() textbackground() (1) malloc() inputs() create() sizeof() (2) sizeof() fwrite() fopen() save()
29、 fclose() (3) malloc() fread() feop() fopen() sizeof() load() fclose() ( 4) insert()
30、 inputs() malloc() strcmp() (5) putchar() strcmp() getch() delete() (6) inputs() strcpy() strlen(
31、)
(7)
search()
strcmp()
七、主控模块和部分子模块
开始
主菜单
选择功能
存入学生信息
删除学生信息
显示学生信息
查询学生信息
保存学生信息
读取学生信息
插入学生信息
退 出 系 统
结束
八、附件
#include
32、stdlib.h> /*I/O函数*/
#include
33、void CAIDANG() { printf(" \t \t \t (欢迎使用本班级档案管理系统)\t\t\t\t\n"); printf("★*★*★*★*★*★*★*★*★*★ 欢迎进入我们的系统 ★*★*★*★*★*★*★*★*★*★\n\n"); printf(" 湖南工程学院0783班C语言课程设计《班级档案管理系统》欢迎您!\n\n"); printf("1.录入学生资料\t\t\t\t\t4.查询学生信息\n\n"); printf("2.修改学生信息\t\t\t\t\t5.删除学生信息\n\n"); printf("3.保存学生信息\t\t\t\t\
34、t0.退出档案系统\n\n"); printf(" \n"); printf("★*★*★*★*★*★*★*★*★*★ 欢迎进入本系统 ★*★*★*★*★*★*★*★*★*★\n"); } /*文本颜色*/ void color() { textbackground(8); textcolor(9); clrscr(); } void Wrong() { printf("\n对不起您的输入错误!\n"); } void SORRY() { printf("\n对不起该同学现没有任何信息!\n"); } void printe(LB_1 *p)
35、/* 本函数用于输出英文 */ { printf(" %-2s %s\t %s\t%s\t %d\t \n",p->XINXI.num,p->XINXI.name,p->XINXI.sex,p->XINXI.address,p->XINXI.age); } /* 该函数用于定位链表中符合要求的接点,并返回该指针 */ LB_1 *Locate(LB_2 l,char findmess[],char nameornum[]) { LB_1 *r; if(strcmp(nameornum,"num")==0) /* 按学号查询
36、 */ { r=l->next; while(r!=NULL) { if(strcmp(r->XINXI.num,findmess)==0) return r; r=r->next; } } else if(strcmp(nameornum,"name")==0) /* 按姓名查询 */ { r=l->next; while(r!=NUL
37、L) { if(strcmp(r->XINXI.name,findmess)==0) return r; r=r->next; } } return 0; } /*以下是增加学生信息的函数*/ void TIANJIA(LB_2 l) { LB_1 *p,*r,*s; char num[13]; r=l; s=l->next; while(r->next!=NULL) /*些处循环一直到最后*/ r=r->next; while(1) { printf(" 请输入添
38、加的学生学号(输入'0'返回上一级菜单:)"); scanf("%s",num); if(strcmp(num,"0")==0) break; while(s) { if(strcmp(s->XINXI.num,num)==0) { printf("(必看提示):学号为'%s'的学生已有信息,若要修改请你输入'2 修改'!\n",num); printe(s); printf("\n"); return; } s=s->next; } p=(LB_1 *)malloc(si
39、zeof(LB_1)); strcpy(p->XINXI.num,num); printf(" 请你输入学号:"); scanf("%s",p->XINXI.num); getchar(); printf(" 请你输入姓名:"); scanf("%s",p->XINXI.name); getchar(); printf(" 请你输入性别:"); scanf("%s",p->XINXI.sex); getchar(); printf(" 请你输入地址:"); scanf("%s",p->XINXI.address); getc
40、har(); printf(" 请你输入年龄:"); scanf("%d",&p->XINXI.age); getchar(); /* 下面是把指针变量转到链表的下一个结点中以便循环的时候使用 */ p->next=NULL; r->next=p; r=p; M=1; } } /*以下是删除学生信息的函数*/ void SHANCHU(LB_2 l) { int sel; LB_1 *p,*r; char findmess[20]; if(!l->next) { printf("\n******(必看提示):对不起,现
41、文件中没有信息:所以您不能查询!\n"); return; } printf("\n <必看提示> <以学号删除请输入1\n> <以姓名删除请输入2\n> PLEASE:"); scanf("%d",&sel); if(sel==1) { printf("请输入要删除的学生的学号PLEASE:"); scanf("%s",findmess); p=Locate(l,findmess,"num"); if(p) { r=l; while(r->next!=p) r=r->next; r->next=p->next;
42、 free(p); printf("\n*******(必看提示):该学生的信息已完全删除成功!\n"); M=1; } else SORRY(); } else if(sel==2) { printf("请输入要删除的学生的姓名PLEASE:"); scanf("%s",findmess); p=Locate(l,findmess,"name"); if(p) { r=l; while(r->next!=p) r=r->next; r->next=p->next; free
43、p); printf("\n******(必看提示):该学生信息已成功删除!\n"); M=1; } else SORRY(); } else Wrong(); } /*以下是查询学生信息*/ void CHAXIONG(LB_2 l) { int sel; char findmess[20]; LB_1 *p; if(!l->next) { printf("\n******(必看提示):对不起,现文件中没有信息:所以您不能查询!\n"); return; } printf("\n以学号查询请输入1:\n以姓
44、名查询请输入2:\n以性别查询请输入3:\n以性别查询请输入4:\n PLEASE:"); scanf("%d",&sel); if(sel==1)/*输入学号查询*/ { printf("请你输入要查找的学号:"); scanf("%s",findmess); p=Locate(l,findmess,"num"); if(p) { printf("\t\t\t\t查找结果\n"); printf(" 学号:%s\n姓名:%s\n性别:%s\n地址:%s\n年龄:%d\n",p->XINXI.num,p->XINXI.name,p->XINXI.sex,p
45、>XINXI.address,p->XINXI.age); } else SORRY(); } if(sel==2) /* 输入姓名查询 */ { printf("请你输入要查找的姓名:"); scanf("%s",findmess); p=Locate(l,findmess,"name"); if(p) { printf("\t\t\t\t查找结果\n"); printf(" 学号:%s\n姓名:%s\n性别:%s\n地址:%s\n年龄:%d\n",p->XINXI.num,p->XINXI.name,p->XINXI.sex,p->
46、XINXI.address,p->XINXI.age); } else SORRY(); } else Wrong(); } /*以下是修改学生信息的函数*/ void XIUGEI(LB_2 l) { LB_1 *p; long int i,j; char findmess[20]; if(!l->next) { printf("\n(必看提示):对不起,现文件中没有信息:所以您不能查询!\n"); return; } for(i=1;i<=2;i++) { printf("\n\n\n\n\n");
47、 printf("请输入密码:"); scanf("%s",&j); if(j==1234)break; else {if(j!=1234) return(CAIDANG()); } } printf("请你输入要修改的学生学号:"); scanf("%s",findmess); p=Locate(l,findmess,"num"); if(p) { printf("请你输入新学号(原来是%s):",p->XINXI.num); scanf("%s",p->XINXI.num);
48、 printf("请你输入新姓名(原来是%s):",p->XINXI.name); scanf("%s",p->XINXI.name); printf("请你输入新性别(原来是%s):",p->XINXI.sex); scanf("%s",p->XINXI.sex); printf("请你输入新地址(原来是%s):",p->XINXI.address); scanf("%s",p->XINXI.address); printf("请你输入新年龄(原来是%d):",p->XINXI.age); scanf("%s",p
49、>XINXI.age); getchar(); M=1; } else SORRY(); } /*保存在文件中*/ void BAOCONG(LB_2 l) { FILE* fp; LB_1 *p; int flag=1,count=0; fp=fopen("c:\\lyg","wr"); if(fp==NULL) { printf("\n=====>提示:重新打开文件时发生错误!\n"); exit(1); } p=l->next; while(p) { if(fwrite(p,sizeof(LB_1)
50、1,fp)==1) { p=p->next; count++; } else { flag=0; break; } } if(flag) { printf("\n 提示;正在保存文件 共保存了%d条信息\n",count);M=0; } fclose(fp); } /*以下是主函数*/ void main() { LB_2 l;/* 连表 */ FILE *fp; /* 文件指针 */ int sel;long i,j,d; char ch; char jian; int co






