600字范文,内容丰富有趣,生活中的好帮手!
600字范文 > C语言课程设计项目——职工信息管理系统

C语言课程设计项目——职工信息管理系统

时间:2018-08-18 19:58:14

相关推荐

C语言课程设计项目——职工信息管理系统

名人说:一花独放不是春,百花齐放花满园。——《增广贤文》

作者:Code_流苏(CSDN)(一个喜欢古诗词和编程的Coder😊)

目录

一、整体框架1、整体模块2、系统说明3、数据类型说明 二、主要功能函数分析1、注册登录2、录入职工信息3、显示职工信息4、修改职工信息5、删除职工信息6、保存职工信息 三、完整代码及注释四、运行页面展示五、总结与收获

以下代码个人分享出来,仅供学习交流,且仅在CSDN平台发布,未经授权禁止二次转发。

一、整体框架

1、整体模块
2、系统说明

《职工信息管理系统》用链表,文件设计方法,各部分利用链表运行,结构清晰,较好地利用了链表等数据类型,主要语句加了上适当的注释,将难以理解的过程,变得更加简洁易懂。

该系统能够实现对职工信息的输入、显示、保存、删除、修改,特别还有管理员的注册与登录等操作。在设计的过程中,建立了清晰的结构体,能进行简单的界面设计,C语言中的基本语句、函数、数组、结构体、文件等。

本程序开发环境为Dev c++ MinGW GCC10.3。

3、数据类型说明

二、主要功能函数分析

1、注册登录

1️⃣代码

//注册账号void add_user(void){// FILE *fp; char str[101]; system("cls"); printf("\n");printf("\t\t\t请输入账号:\n\n\t\t\t "); scanf("%s",str);while(strlen(str)>16 || check_exist(str)) //使用循环而不是递归,并且增加一个检查账号是否存在的函数{if(strlen(str)>16)printf("\t\t账号长度大于16位,请重新输入\n");elseprintf("\t\t该账号已被注册,请重新注册\n");system("PAUSE"); system("cls"); printf("\n"); printf("\t\t\t请输入账号:\n\n\t\t\t "); scanf("%s",str);}strcpy(user[user_count].ID,str); //使用user_count而不是iprintf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);while(strlen(str)>16){system("cls");printf("\n");printf("\t\t密码长度大于16位,请重新输入\n\n");printf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);} strcpy(user[user_count].password,str); //使用user_count而不是iprintf("\t\t\t请再次输入密码:\n\n\t\t\t "); scanf("%s",str); while(strcmp(user[user_count].password,str)!=0) //使用循环而不是递归{printf("\t\t两次密码不一致,请重新输入\n\n"); printf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);while(strlen(str)>16){system("cls");printf("\n");printf("\t\t密码长度大于16位,请重新输入\n\n");printf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);} strcpy(user[user_count].password,str); //使用user_count而不是iprintf("\t\t\t请再次输入密码:\n\n\t\t\t "); scanf("%s",str); }save_user();//将账号写入磁盘 printf("\t\t\t账号申请成功\n\n\t\t\t"); user_count++;if(user_count>=1010) //检查是否超出数组范围{printf("\t\t已达到最大账号数量,无法再添加新账号\n\n");}system("PAUSE");user_menu(); }//检查账号是否存在bool check_exist(char* str) //增加一个检查账号是否存在的函数,返回true或false{int i;for(i=0;i<user_count;i++)if(strcmp(user[i].ID,str)==0)return true;return false;}//登录账号void login_user(void){int i,flag=0;char str[20];system("cls"); printf("\n");printf("\t\t\t请输入账号:\n\n\t\t\t ");scanf("%s",str);for(i=0;i<user_count;i++)if(strcmp(user[i].ID,str)==0){flag=1;break;}if(flag==0){int n;printf("\t\t\t该账号不存在!\n\t\t\t请输入你的选择\n");printf("\t\t\t<---------------->\n"); printf("\t\t\t |0.返回上层菜单 |\n");printf("\t\t\t<---------------->\n");printf("\t\t\t |1.退出系统|\n");printf("\t\t\t<---------------->\n"); printf("\t\t\t请输入你的选择:\n");printf("\t\t\t");scanf("%d",&n);switch(n){case 0:user_menu();break;case 1:exit(0);break;}system("cls"); printf("\n");login_user(); return;}printf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);while(strcmp(user[i].password,str)!=0){system("cls"); printf("\n");printf("\t\t\t密码错误,请重新输入\n\n\t\t\t\t");scanf("%s",str);}printf("\t\t\t登录成功\n\n\t\t\t");system("PAUSE");choose_menu();}

2️⃣函数实现过程

第一个函数是add_user,其功能是注册账号。首先清空屏幕,然后提示用户输入账号,并用一个字符串str存储。之后用一个循环检查账号的长度是否超过16位,以及账号是否已经存在(调用了第二个函数check_exist)。如果有问题,就让用户重新输入。如果没有问题,就把账号复制到user[user_count].ID中,其中user是一个结构体数组,user_count是一个全局变量,表示当前的账号数量。接下来,提示用户输入密码,并用同样的字符串str存储。然后它用另一个循环检查密码的长度是否超过16位,如果是,就让用户重新输入。如果不是,就把密码复制到user[user_count].password中。然后它提示用户再次输入密码,并用同样的字符串str存储。然后它用第三个循环检查两次输入的密码是否一致,如果不一致,就让用户重新输入。如果一致,就调用第三个函数save_user,把账号信息写入磁盘。然后它打印出账号申请成功的信息,并把user_count加一。最后,它检查是否达到了最大账号数量(1010),如果是,就打印出无法再添加新账号的信息。然后它暂停程序,并返回用户菜单(调用了另一个函数user_menu)。

第二个函数是check_exist,它的功能是检查账号是否存在。首先接受一个字符串参数str,表示要检查的账号。之后用一个循环遍历所有已经注册的账号(存储在结构体数组user中),并用字符串比较函数strcmp判断是否有相同的账号。如果有,就返回真值(true)。如果没有,就返回假值(false)。

第三个函数是login_user,其功能是登录账号。首先清空屏幕,然后提示用户输入账号,并用一个字符串str存储。接着用一个循环遍历所有已经注册的账号(存储在结构体数组user中),并用字符串比较函数strcmp判断是否有相同的账号。如果有,就把一个标志变量flag设为1,并跳出循环。如果没有,就打印出该账号不存在的信息,并让用户选择返回上层菜单(调用了另一个函数user_menu)或退出系统(调用了系统函数exit)。然后它清空屏幕,并递归地调用自己(这里可以改成循环)。如果找到了相同的账号,就提示用户输入密码,并用同样的字符串str存储。然后它用一个循环检查密码是否正确(和对应的user[i].password比较),如果不正确,就让用户重新输入。如果正确,就打印出登录成功的信息,并暂停程序。然后它进入选择菜单(调用了另一个函数choose_menu)。

2、录入职工信息

1️⃣代码

//录入信息函数void Add(List L){Position TmpCell;int number;char n[20];printf("\n请输入所要创建的职工号: ");//提示输入职工号scanf("%d",&number); if(!IsLast(FindNumPrevious(number,L),L)) //连续调用 职工号前驱指针查找函数 判断链尾函数,判断该职工号是否已存在{printf("\n职工号 %d 已存在!!!\n\n",number);TurnBack(); //调用返回上一菜单函数return; //退出并返回上一级菜单}printf("\n请输入该职工的姓名: "); //保存职工姓名scanf("%s",n); if(!IsLast(FindNamePrevious(n,L),L))//连续调用 职工姓名前驱指针查找函数 判断链尾函数,判断该职工姓名是否已存在{printf("\n职工姓名 %s 已存在!!!\n\n",n);TurnBack(); //调用返回上一菜单函数return; //退出并返回上一级菜单}TmpCell=(Position)malloc(sizeof(struct Employee)); //创建新结点if(TmpCell==NULL){printf("\n添加失败,内存不足!!!\n\n"); //添加失败,提示内存不足system("pause"); //暂停屏幕显示return; //返回上一级菜单}TmpCell->num=number; //保存职工号strcpy(TmpCell->name,n); //保存姓名printf("\n请输入该职工的工作部门: "); //保存工作部门scanf("%s",TmpCell->department);printf("\n请输入该职工的职称: "); //保存职称scanf("%s",TmpCell->Title); printf("\n请输入该职工的入厂时间(格式为:年/月/日): "); //保存入厂时间scanf("%s",TmpCell->time);printf("\n请输入该职工的工资(单位:元): "); //保存工资scanf("%d",&TmpCell->money); TmpCell->Next=L->Next; //将结点TmpCell插入到链表中L->Next=TmpCell; printf("\n职工 %s 的信息创建成功!!!\n",TmpCell->name); //提示创建成功Save(L);//调用 信息保存函数TurnBack(); //调用 返回上一菜单函数return;//退出并返回上一级菜单}

2️⃣函数实现过程

这个函数是Add,它的功能是录入一个新员工的信息,并把它插入到链表中。其中接受一个参数L,表示一个员工链表。首先定义了一个指针变量TmpCell用来创建新结点,一个整型变量number用来存储职工号,一个字符数组变量n用来存储姓名。然后它打印出提示信息,让用户输入要创建的职工号,并用整型变量number存储。接着它调用了两个函数:FindNumPreviousIsLast,传入职工号和链表,判断该职工号是否已经存在于链表中。如果存在,就打印出错误信息,并调用另一个函数TurnBack返回上一菜单,并退出函数。如果不存在,就继续打印出提示信息,让用户输入该员工的姓名,并用字符数组变量n存储。之后它调用了两个函数:FindNamePreviousIsLast,传入姓名和链表,判断该姓名是否已经存在于链表中。如果存在,就也打印出错误信息,并调用另一个函数TurnBack返回上一菜单,并退出函数。如果不存在,就为新结点分配内存空间(调用了系统函数malloc),并检查是否分配成功(即TmpCell是否为空)。如果不成功,就打印出内存不足的信息,并暂停程序(调用了系统函数pause),并退出函数。如果成功,就把职工号和姓名分别复制到新结点的相应字段中(使用了字符串复制函数strcpy)。接着它继续打印出提示信息,让用户输入该员工的其他信息,包括工作部门、职称、入厂时间和工资,并分别复制到新结点的相应字段中。然后它把新结点插入到链表的头部(即头结点的下一个位置),并打印出创建成功的信息。紧接着它调用了另一个函数Save,把链表中的员工信息保存到磁盘中。最后,调用了另一个函数TurnBack返回上一菜单,并退出函数。

3、显示职工信息

1️⃣代码

//职工信息打印函数void PrintEmployee(Position P){printf("\n该职工信息如下:\n");printf("- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");printf(" 职工号 姓名工作部门职称 入厂时间工资\n"); printf("- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");printf(" %-d %-s %-s %-s %-s %-d\n",P->num,P->name,P->department,P->Title,P->time,P->money);printf("\n\n- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");}//职工号显示函数void ViewNum(List L) {Position P;int number;printf("\n请输入所要查询的职工号: ");scanf("%d",&number);P=FindNumPrevious(number,L); //调用职工号前驱指针查找函数,获得所需显示结点的前一结点if(IsLast(P,L)==1)//判断是否存在该员工printf("\n无职工号为 %d 的员工!!!\n\n",number);elsePrintEmployee(P->Next);//调用职工信息打印函数TurnBack(); //调用返回上一菜单函数return;//返回上一菜单}//部门信息显示函数void ViewDepartment(List L){Position P;PtrToTitle P1,L1;char c[20];int num,money;L1=NULL;L1=MakeEmptyTitle(L1); //调用职称链表创建函数num=money=0;printf("请输入所要查询的部门名称: ");scanf("%s",c);P=L->Next;while(P!=NULL&&strcmp(c,P->department)!=0)P=P->Next;if(P==NULL){printf("\n无名称为 %s 的部门\n\n",c);TurnBack();//调用返回上一菜单函数return;}printf("\n该部门职工信息如下:\n");printf("- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");printf(" 职工号 姓名 工作部门职称入厂时间 工资\t\n"); printf("- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");P=L->Next;while(P!=NULL){if(strcmp(c,P->department)==0){printf(" %-d %-s %-s %-s %-s%-d\n",P->num,P->name,P->department,P->Title,P->time,P->money);L1=InsertTitle(P->Title,L1);num++;money+=P->money;}P=P->Next;}printf("\n\n- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");printf("该部门的统计情况如下:\n 总人数为: %d 人\n 平均工资为: %.2f 元\n",num,(float)money/num);P1=L1->Next;while(P1!=NULL){printf(" 职称为 %s 的共: %d 人\n",P1->title,P1->num);P1=P1->Next;}putchar('\n');TurnBack(); //调用返回上一菜单函数return;//退出并返回上一级菜单}

2️⃣函数实现过程

这个函数是PrintEmployee,其功能是打印出一个员工结点的信息。接受一个参数P,表示一个员工结点。接着先打印出提示信息,表示要显示的员工信息。然后它打印出一个表格的表头,包括职工号、姓名、工作部门、职称、入厂时间和工资等字段。之后它打印出指针变量P所指向的结点的相应字段的值,按照一定的格式对齐。最后,它打印出一个表格的表尾,表示结束。

第一个函数是ViewNum,该函数的功能是显示某个职工号对应的员工信息。接受一个参数L,表示一个员工链表。它首先打印出提示信息,让用户输入要查询的职工号,并用一个整型变量number存储。然后它调用了另一个函数FindNumPrevious,传入职工号和链表,返回该职工号对应的结点的前一个结点,用一个指针变量P存储。然后它调用了另一个函数IsLast,传入指针和链表,判断该指针是否指向链表的最后一个结点(即空结点)。如果是,就说明没有找到该职工号对应的员工,就打印出错误信息。如果不是,就说明找到了该职工号对应的员工,就调用另一个函数PrintEmployee,传入指针的下一个结点(即目标结点),打印出该员工的信息。最后,它调用了另一个函数TurnBack,返回上一菜单,并退出函数。

第二个函数是ViewDepartment,其功能是显示某个部门的员工信息和统计情况。接受一个参数L,表示一个员工链表。接着定义了几个变量:一个指针变量P用来遍历链表,一个指向职称结构体的指针变量P1和一个指向职称链表的指针变量L1用来统计不同职称的人数,一个字符数组变量c用来存储要查询的部门名称,两个整型变量nummoney用来统计部门的总人数和总工资。然后它把职称链表初始化为空(调用了另一个函数MakeEmptyTitle),并把总人数和总工资设为0。之后它打印出提示信息,让用户输入要查询的部门名称,并用字符数组变量c存储。然后它把指针P指向链表的第一个结点(即头结点的下一个结点),并用一个循环找到第一个属于该部门的员工结点。如果没有找到(即P为空),就打印出错误信息,并调用另一个函数TurnBack返回上一菜单,并退出函数。如果找到了(即P不为空),就打印出该部门员工信息的表头,并把指针P重新指向链表的第一个结点(即头结点的下一个结点)。然后它用另一个循环遍历整个链表,如果某个结点属于该部门(即部门名称和字符数组变量c相同),就打印出该员工的信息,并把该员工的职称插入到职称链表中(调用了另一个函数InsertTitle),并把总人数加一,总工资加上该员工的工资。循环结束后,它打印出该部门的统计情况,包括总人数、平均工资和不同职称的人数(遍历职称链表)。最后,它调用另一个函数TurnBack返回上一菜单,并退出函数。

4、修改职工信息

1️⃣代码

//信息修改函数void Mod(List L) {while(1){char a;Position P;system("cls");//实现清屏ModMeun(); //调用修改菜单fflush(stdin);//清除键盘缓冲区a=Test1(getchar(),'1','3'); //调用菜单输入检测函数switch(a){case '1'://职工号修改{int number;system("cls"); printf("\n请输入所要修改的职工信息的职工号: ");scanf("%d",&number);P=FindNumPrevious(number,L); //调用职工号前驱指针查找函数,获得所需显示结点的前一结点if(IsLast(P,L)==1)//判断是否存在该员工{printf("\n无职工号为 %d 的员工!!!\n\n",number);TurnBack(); //调用返回上一菜单函数}elseMod1(P->Next,L);//调用修改的部分函数break; //返回上一菜单}case '2':return;}}}//修改的部分函数 void Mod1(Position P,List L){while(1){char a;PrintEmployee(P);//调用职工信息打印函数ModMeun1(); //调用修改菜单fflush(stdin);//清除键盘缓冲区a=Test1(getchar(),'1','7'); //调用菜单输入检测函数switch(a){case '1': system("cls"); ModNum(P,L); break; //职工号修改case '2': system("cls"); ModName(P,L); break; //职工姓名修改case '3': return;}}}//职工号修改函数void ModNum(Position P,List L){int b; printf("\n请输入新的职工号: "); scanf("%d",&b); if(!IsLast(FindNumPrevious(b,L),L))//连续调用 职工号前驱指针查找函数 判断链尾函数,判断该职工号是否已存在printf("\n职工号 %d 已存在!!!\n\n",b);else{P->num=b; Save(L); //调用信息保存函数}TurnBack();//调用返回上一菜单函数return; //返回上一级菜单并退出}//职工姓名修改函数void ModName(Position P,List L) {char c[20]; printf("\n请输入新的职工姓名: "); scanf("%s",c); if(!IsLast(FindNamePrevious(c,L),L))//连续调用 职工姓名前驱指针查找函数 判断链尾函数,判断该职工姓名是否已存在printf("\n职工姓名 %s 已存在!!!\n\n",c);else{strcpy(P->name,c); Save(L); //调用信息保存函数}TurnBack();//调用返回上一菜单函数return; //返回上一级菜单并退出}

2️⃣函数实现过程

第一个函数是Mod,其功能是修改员工信息。接受一个参数L,表示一个员工链表。它用一个无限循环实现菜单的重复显示和选择。之后它首先清空屏幕(调用了系统函数system),然后调用了另一个函数ModMeun,显示修改菜单的选项。然后它清除键盘缓冲区(调用了系统函数fflush),并让用户输入一个字符,并用另一个函数Test1检测该字符是否在'1''3'之间。如果是,就根据字符的值执行相应的操作。如果是'1',就表示要修改职工号,就进入第二个函数Mod1的调用。如果是'2',就表示要返回上一菜单,就退出循环和函数。

第二个函数是Mod1,该函数的功能是修改某个员工结点的信息。接受两个参数:一个指针变量P表示要修改的员工结点,一个指针变量L表示员工链表。它用了一个无限循环实现菜单的重复显示和选择。接着先调用了另一个函数PrintEmployee,传入指针变量P,打印出该员工的信息。然后它调用了另一个函数ModMeun1,显示修改菜单的选项。然后它清除键盘缓冲区(调用了系统函数fflush),并让用户输入一个字符,并用另一个函数Test1检测该字符是否在'1''7'之间。如果是,就根据字符的值执行相应的操作。如果是'1',就表示要修改职工号,就清空屏幕(调用了系统函数system),并进入第三个函数ModNum的调用。如果是'2',就表示要修改姓名,就清空屏幕(调用了系统函数system),并进入第四个函数ModName的调用。如果是'3',就表示要返回上一菜单,就退出循环和函数。

第三个函数是ModNum,其功能是修改某个员工结点的职工号。接受两个参数:一个指针变量P表示要修改的员工结点,一个指针变量L表示员工链表。它首先定义了一个整型变量b用来存储新的职工号,并打印出提示信息让用户输入新的职工号,并用整型变量b存储。然后它调用了两个函数:FindNumPreviousIsLast,传入新的职工号和链表,判断该职工号是否已经存在于链表中。如果存在,就打印出错误信息。如果不存在,就把新的职工号复制到指针变量P所指向的结点的相应字段中,并调用另一个函数Save把链表中的员工信息保存到磁盘中。最后,它调用了另一个函数TurnBack返回上一菜单,并退出函数。

第四个函数是ModName,该函数功能是修改某个员工结点的姓名。接受两个参数:一个指针变量P表示要修改的员工结点,一个指针变量L表示员工链表。该函数首先定义了一个字符数组变量c用来存储新的姓名,并打印出提示信息让用户输入新的姓名,并用字符数组变量c存储。然后它调用了两个函数:FindNamePreviousIsLast,传入新的姓名和链表,判断该姓名是否已经存在于链表中。如果存在,就打印出错误信息。如果不存在,就把新的姓名复制到指针变量P所指向的结点的相应字段中(使用了字符串复制函数strcpy),并调用另一个函数Save把链表中的员工信息保存到磁盘中。最后,它调用了另一个函数TurnBack返回上一菜单,并退出函数。

5、删除职工信息

1️⃣代码

//职工号删除函数void DeleteNum(List L) {Position P,TmpCell;int number;printf("\n请输入所要删除的职工信息的职工号: ");scanf("%d",&number);P=FindNumPrevious(number,L); //调用职工号前驱指针查找函数,获得所需显示结点的前一结点if(IsLast(P,L)==1)//判断是否存在该员工printf("\n无职工号为 %d 的员工!!!\n\n删除失败!!!\n\n",number);else{PrintEmployee(P->Next);//调用职工信息打印函数fflush(stdin); //清除键盘缓冲区printf("\n是否确认要删除?回复'Y'/'N'\n");if(getchar()=='Y'){TmpCell=P->Next;P->Next=TmpCell->Next; free(TmpCell);printf("\n删除成功!!!\n\n");Save(L); //调用信息保存函数}}TurnBack(); //调用返回上一菜单函数return;//退出并返回上一级菜单}

2️⃣函数实现过程

这个函数是DeleteNum,它的功能是删除某个职工号对应的员工信息。接受一个参数L,表示一个员工链表。它首先定义了两个指针变量:一个指针变量P用来存储要删除的员工结点的前一个结点,一个指针变量TmpCell用来存储要删除的员工结点。其还定义了一个整型变量number用来存储要删除的职工号,并打印出提示信息让用户输入要删除的职工号,并用整型变量number存储。然后它调用了另一个函数FindNumPrevious,传入职工号和链表,返回该职工号对应的结点的前一个结点,用指针变量P存储。然后它调用了另一个函数IsLast,传入指针和链表,判断该指针是否指向链表的最后一个结点(即空结点)。如果是,就说明没有找到该职工号对应的员工,就打印出错误信息。如果不是,就说明找到了该职工号对应的员工,就调用另一个函数PrintEmployee,传入指针的下一个结点(即目标结点),打印出该员工的信息。然后它清除键盘缓冲区(调用了系统函数fflush),并打印出确认信息,让用户输入'Y''N'表示是否要删除该员工。如果用户输入'Y',就把指针变量TmpCell指向要删除的员工结点(即指针变量P的下一个结点),然后把指针变量P的下一个结点改为指针变量TmpCell的下一个结点(即跳过要删除的结点),然后释放指针变量TmpCell所指向的内存空间(调用了系统函数free),并打印出删除成功的信息。然后它调用了另一个函数Save,把链表中的员工信息保存到磁盘中。最后,它调用了另一个函数TurnBack,返回上一菜单,并退出函数。

6、保存职工信息

1️⃣代码

//信息保存函数 void Save(List L) {FILE *fp; //文件指针Position P;L=Sort(L); //调用链表冒泡排序函数P=L;if((fp=fopen("职工信息.txt","w+"))==NULL) //打开"职工信息.txt"文本文件{printf("无法打开文件!!!\n");system("pause"); //暂停屏幕显示return;}fp=fopen("职工信息.txt","w+"); //以读写的方式打开"职工信息.txt"文本文件while(P->Next!=NULL) //将内存中的数据输出到磁盘中{P=P->Next; //信息从第一个有效结点开始保存,循环指向下一个有效结点if(fprintf(fp,"%d %s %s %s %s %d\n",P->num,P->name,P->department,P->Title,P->time,P->money)<0) break; //向文件写入信息}printf("\n职工信息保存成功!!!\n\n");fclose(fp);return;}

2️⃣函数实现过程

这个函数是Save,其功能是把链表中的员工信息保存到磁盘中。其中接受一个参数L,表示一个员工链表。首先它定义了一个文件指针变量fp用来操作文件,和一个指针变量P用来遍历链表。然后它调用了另一个函数Sort,传入链表,对链表中的员工信息进行冒泡排序。接着它把指针变量P指向链表的头结点,并尝试以读写的方式打开一个名为"职工信息.txt"的文本文件,并用文件指针变量fp存储。如果打开失败(即fp为空),就打印出错误信息,并暂停程序(调用了系统函数system),并退出函数。如果打开成功(即fp不为空),就再次以读写的方式打开该文件(这里可以省略)。然后它用一个循环遍历链表中的所有结点(从第一个有效结点开始),并用文件写入函数fprintf把每个结点的员工信息按照一定的格式写入到文件中。如果写入失败(即返回值小于0),就跳出循环。循环结束后,它打印出保存成功的信息,并关闭文件(调用了系统函数fclose),并退出函数。

三、完整代码及注释

//创作者:Code_流苏(CSDN)//未经允许,禁止转载发布,可自己学习使用//头文件声明 #include<stdio.h>#include<stdlib.h>#include<math.h>#include<algorithm> #include<string.h>//结构体声明、职工工资结构体 struct Employee;//职工工资结构体声明typedef struct Employee *PtrToNode;//结构体指针定义typedef PtrToNode List; //链表头指针定义typedef PtrToNode Position; //链表结点指针定义 //职称结构体struct Title; //职称结构体声明typedef struct Title *PtrToTitle; //结构体指针定义//链表函数声明、空链表创建函数 int IsEmpty(List L); //判断空链表函数int IsLast(Position P,List L); //判断链尾函数Position FindNumPrevious(int number,List L); //职工号前驱指针查找函数 Position FindNamePrevious(char name[],List L); //职工姓名前驱指针查找函数 List Sort(List L);//链表冒泡排序函数PtrToTitle MakeEmptyTitle(PtrToTitle L1); //空职称链表创建函数PtrToTitle InsertTitle(char t[20],PtrToTitle L1); //职称插入函数//文件函数声明List Init(List L); //初始化函数void Save(List L); //信息保存函数//菜单函数声明void MainMeun(void);//主菜单void ViewMeun(); //显示菜单void ModMeun(); //修改菜单void ModMeun1(); //修改的部分菜单//职工管理函数声明void Add(List L); //信息录入函数void View(List L); //信息显示函数void ViewNum(List L); //职工号显示函数void ViewDepartment(List L); //部门信息显示函数//登录 void user_menu(void);//账号菜单void add_user(void);//注册账号 void login_user(void);//登录账号void reset_password(void);//修改密码void save_user(void);//将账号写入磁盘void choose_menu(void);//选择菜单bool check_exist(char* str);//修改 void Mod(List L); //信息修改函数void Mod1(Position P,List L); //修改的部分函数void ModNum(Position P,List L); //职工号修改函数void ModName(Position P,List L); //职工姓名修改函数//删除 void DeleteList(List L);//链表删除函数void DeleteNum(List L); //职工号删除函数void PrintEmployee(Position P); //职工工资打印函数void TurnBack(); //返回上一菜单函数char Test1(char a,char b,char c); //菜单输入检测函数int user_count=0;//定义职工工资结构体struct Employee {int num;//职工号char name[20]; //姓名char department[20]; //工作部门char Title[20]; //职称char time[10]; //入厂时间 年/月/日 /6/29 int money; //工资Position Next; //Next指针 (指向下一结构体)};//职称结构体struct Title{char title[20]; //职称名称int num; //部门职称人数struct Title* Next; //Next指针};struct asccount{char ID[20]; char password[20]; }user[1010];//主函数int main(){user_menu();List L=NULL;char a;L=Init(L);printf("\n\t\t输入回车键继续"); getchar();while(1){system("color be");system("cls"); //实现清屏MainMeun();//调用 主菜单显示函数fflush(stdin); //清除键盘缓冲区a=Test1(getchar(),'0','7'); //菜单输入检测函数switch(a){case '0': system("cls"); choose_menu(); break;case '1': system("cls"); Add(L); break;//调用 信息录入函数case '2': system("cls"); View(L);break;//调用 信息显示函数 case '3': system("cls"); Mod(L); break;//调用 信息修改函数case '4': system("cls"); DeleteNum(L);break;//调用 信息删除函数case '5': system("cls"); Save(L);system("pause"); break; //调用 信息保存函数case '6': return 0; //退出系统}}return 0;}//链表函数//空链表创建函数List MakeEmpty(List L){if(L) //相当于 if(L!=NULL) ,即指针L指向的空间不为空DeleteList(L); //删除原先链表L=(List)malloc(sizeof(struct Employee)); //创建新的空链表if(!L) //相当于 if(L==NULL) ,即指针L指向的空间为空{printf("创建失败,内存不足!!!"); //创建失败,提示内存不足system("pause"); //暂停屏幕显示return NULL; //返回上一级菜单}L->Next=NULL;//Next指针指向空return L; //返回链表头}//空职称链表创建函数struct Title *MakeEmptyTitle(struct Title *L1){if(L1) //相当于 if(L!=NULL) ,即指针L指向的空间不为空{struct Title *P;P=L1->Next; //取链表头后的所有结点L1->Next=NULL; //链表头指向空结点while(P!=NULL) //依次释放链表头后所有结点的空间{free(P);P=P->Next;}}L1=(struct Title *)malloc(sizeof(struct Title)); //创建新的空链表if(!L1) //相当于 if(L==NULL) ,即指针L指向的空间为空{printf("创建失败,内存不足!!!"); //创建失败,提示内存不足system("pause"); //暂停屏幕显示return NULL; //返回上一级菜单}L1->Next=NULL;//Next指针指向空return L1; //返回链表头}//职称插入函数PtrToTitle InsertTitle(char t[20],PtrToTitle L1){PtrToTitle P,TmpCell;if(L1->Next==NULL)//如果职称链表为空,则直接创建结点{TmpCell=(PtrToTitle)malloc(sizeof(struct Title));if(TmpCell==NULL)printf("\n超出空间!!!\n\n");else//将新建结点插入链表{strcpy(TmpCell->title,t);TmpCell->Next=L1->Next;L1->Next=TmpCell;TmpCell->num=1;}}else{P=L1->Next;while(P!=NULL&&strcmp(P->title,t)!=0)P=P->Next;if(P==NULL){TmpCell=(PtrToTitle)malloc(sizeof(struct Title));if(TmpCell==NULL)printf("\n超出空间!!!\n\n");else//将新建结点插入链表{strcpy(TmpCell->title,t);TmpCell->Next=L1->Next;L1->Next=TmpCell;TmpCell->num=1;}}elseP->num++;}return L1;}//判断空链表函数int IsEmpty(List L) {return L->Next==NULL; //头结点的Next指针为空,则链表为空,返回值为1}//判断链尾函数int IsLast(Position P,List L) {return P->Next==NULL; //结点P的Next指针为空,则P为最后一个结点,返回值为1}//链表删除函数void DeleteList(List L) {Position P;P=L->Next; //取链表头后的所有结点L->Next=NULL; //链表头指向空结点while(P!=NULL) //依次释放链表头后所有结点的空间{free(P);P=P->Next;}}//职工号前驱指针查找函数 Position FindNumPrevious(int number,List L) {Position P;P=L;while(P->Next!=NULL&&P->Next->num!=number) //判断P的Next指针是否为空,且P的下一个结点的职工号是否为查找的职工号P=P->Next;//查找下一个return P;//返回该职工号的前驱指针}//职工姓名前驱指针查找函数 Position FindNamePrevious(char name[],List L) {Position P;P=L;while(P->Next!=NULL&&strcmp(name,P->Next->name)!=0) //判断P的Next指针是否为空,且P的下一个结点的职工姓名是否为查找的职工姓名P=P->Next; //查找下一个return P; //返回该职工号的前驱指针}//链表选择排序函数List Sort(List L){Position P,Tmp1,Tmp2,Min;int i,j,num=0;P=L->Next;while(P!=NULL) //获取总人数{num++;P=P->Next;}for(j=0;j<num-1;j++) //通过总人数控制循环{P=L;for(i=0;i<j;i++) //找到已排序部分的末尾{P=P->Next;}Tmp1=P->Next; //未排序部分的第一个元素Tmp2=Tmp1->Next; //未排序部分的第二个元素Min=Tmp1; //假设最小元素为第一个元素while(Tmp2!=NULL) //遍历未排序部分{if(Tmp2->num<Min->num) //升序{Min=Tmp2; //更新最小元素}Tmp2=Tmp2->Next; //指向下一个元素}if(Min!=Tmp1) //如果最小元素不是第一个元素,就交换它们的位置{Tmp2=Min->Next; //保存最小元素的后继节点P->Next=Min; //将最小元素放到已排序部分的末尾Min->Next=Tmp1; //将原来的第一个元素放到最小元素的后面while(Tmp1->Next!=Min) //找到原来第一个元素的前驱节点{Tmp1=Tmp1->Next;}Tmp1->Next=Tmp2; //将原来第一个元素的前驱节点指向最小元素的后继节点}}return L; }//注册登录菜单函数 void user_menu(void) {int choose;system("color be");system("cls");printf("\n\n\t\t*****************************************");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t 欢迎来到职工工资管理系统\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t登录账号请按1\t\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t注册账号请按2\t\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t修改密码请按3\t\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t退出系统请按0\t\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*****************************************");printf("\n\t\t\t\t");printf("\n\t\t\t 请输入选项:\n\t\t\t\t ");scanf("%d",&choose);switch(choose){case 1:login_user(); break;case 2:add_user(); break;case 3:reset_password(); break;case 0:exit(0); default :printf("\n\t\t\t 输入错误,请重新输入\n\n\t\t\t "); system("PAUSE"); system("cls"); user_menu(); }}//注册账号void add_user(void){// FILE *fp; char str[101]; system("cls"); printf("\n");printf("\t\t\t请输入账号:\n\n\t\t\t "); scanf("%s",str);while(strlen(str)>16 || check_exist(str)) //使用循环而不是递归,并且增加一个检查账号是否存在的函数{if(strlen(str)>16)printf("\t\t账号长度大于16位,请重新输入\n");elseprintf("\t\t该账号已被注册,请重新注册\n");system("PAUSE"); system("cls"); printf("\n"); printf("\t\t\t请输入账号:\n\n\t\t\t "); scanf("%s",str);}strcpy(user[user_count].ID,str); //使用user_count而不是iprintf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);while(strlen(str)>16){system("cls");printf("\n");printf("\t\t密码长度大于16位,请重新输入\n\n");printf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);} strcpy(user[user_count].password,str); //使用user_count而不是iprintf("\t\t\t请再次输入密码:\n\n\t\t\t "); scanf("%s",str); while(strcmp(user[user_count].password,str)!=0) //使用循环而不是递归{printf("\t\t两次密码不一致,请重新输入\n\n"); printf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);while(strlen(str)>16){system("cls");printf("\n");printf("\t\t密码长度大于16位,请重新输入\n\n");printf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);} strcpy(user[user_count].password,str); //使用user_count而不是iprintf("\t\t\t请再次输入密码:\n\n\t\t\t "); scanf("%s",str); }save_user();//将账号写入磁盘 printf("\t\t\t账号申请成功\n\n\t\t\t"); user_count++;if(user_count>=1010) //检查是否超出数组范围{printf("\t\t已达到最大账号数量,无法再添加新账号\n\n");}system("PAUSE");user_menu(); }//检查账号是否存在bool check_exist(char* str) //增加一个检查账号是否存在的函数,返回true或false{int i;for(i=0;i<user_count;i++)if(strcmp(user[i].ID,str)==0)return true;return false;}//将账号读入内存void load_user(void){FILE *fp;fp=fopen("账号.txt","r"); while(fscanf(fp,"%s",user[user_count].ID)!=EOF){fscanf(fp,"%s",user[user_count].password); user_count++;if(user_count>=1010) //检查是否超出数组范围{printf("\t\t已达到最大账号数量,无法再读取更多账号\n\n");break;}}fclose(fp);}//将账号写入磁盘void save_user(void){int i;FILE *fp; fp=fopen("账号.txt","w");for(i=0;i<user_count;i++) //使用<user_count而不是<=user_count{fprintf(fp,"%s\n",user[i].ID); fprintf(fp,"%s\n",user[i].password); } fclose(fp); }//登录账号void login_user(void){int i,flag=0;char str[20];system("cls"); printf("\n");printf("\t\t\t请输入账号:\n\n\t\t\t ");scanf("%s",str);for(i=0;i<user_count;i++)if(strcmp(user[i].ID,str)==0){flag=1;break;}if(flag==0){int n;printf("\t\t\t该账号不存在!\n\t\t\t请输入你的选择\n");printf("\t\t\t<---------------->\n"); printf("\t\t\t |0.返回上层菜单 |\n");printf("\t\t\t<---------------->\n");printf("\t\t\t |1.退出系统|\n");printf("\t\t\t<---------------->\n"); printf("\t\t\t请输入你的选择:\n");printf("\t\t\t");scanf("%d",&n);switch(n){case 0:user_menu();break;case 1:exit(0);break;}system("cls"); printf("\n");login_user(); return;}printf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);while(strcmp(user[i].password,str)!=0){system("cls"); printf("\n");printf("\t\t\t密码错误,请重新输入\n\n\t\t\t\t");scanf("%s",str);}printf("\t\t\t登录成功\n\n\t\t\t");system("PAUSE");choose_menu();} //修改密码void reset_password(void){int i,flag=0;char str[20];system("cls"); printf("\n");printf("\t\t\t请输入账号:\n\n\t\t\t ");scanf("%s",str);for(i=0;i<user_count;i++)if(strcmp(user[i].ID,str)==0){flag=1;break;}if(flag==0){printf("\t\t该账号不存在,请重新登录\n\n\t\t\t");system("PAUSE");system("cls"); printf("\n");reset_password(); return;}printf("\t\t\t请输入密码:\n\n\t\t\t ");scanf("%s",str);while(strcmp(user[i].password,str)!=0){system("cls"); printf("\n");printf("\t\t\t密码错误,请重新输入\n\n\t\t\t\t");scanf("%s",str);}printf("\t\t\t请输入新密码\n\n\t\t\t "); scanf("%s",str);while(strlen(str)>16){printf("\t\t密码长度大于16位,请重新输入\n");system("PAUSE"); system("cls"); printf("\n"); scanf("%s",str);} strcpy(user[i].password,str); printf("\t\t\t请再次输入密码:\n\n\t\t\t "); scanf("%s",str); while(strcmp(user[i].password,str)!=0){printf("\t\t两次密码不一致,请重新申请\n\n\t\t\t"); system("PAUSE"); system("cls"); printf("\n"); scanf("%s",str);} save_user();printf("\t\t\t修改成功\n\n\t\t\t"); system("PAUSE");user_menu();}//登录后页面显示选择菜单void choose_menu(void){int choose;while(1){system("cls");printf("\n\n\t\t*****************************************");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t欢迎来到选择菜单管理\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t职工工资管理请按1\t\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*\t返回到上一层请按0\t\t*");printf("\n\t\t*\t\t\t\t\t*");printf("\n\t\t*****************************************");printf("\n\t\t\t\t");printf("\n\t\t\t 请输入选项:\n\t\t\t\t ");scanf("%d",&choose); switch(choose){case 0:system("cls");user_menu(); return;case 1:system("cls");MainMeun(); return;default:printf("\n\t\t\t 输入错误,请重新输入\n\n\t\t\t "); system("PAUSE"); system("cls");} }} //调用菜单函数 显示主菜单void MainMeun(void) //主菜单 {printf("\n\t\t主菜单");printf("\n\t\t*******************************************");printf("\n\t\t* 1、录入信息 *");printf("\n\t\t* 2、显示信息 *");printf("\n\t\t* 3、修改信息 *");printf("\n\t\t* 4、删除信息 *");printf("\n\t\t* 5、保存信息 *");printf("\n\t\t* 6、退出系统 *");printf("\n\t\t* 0、返回上一层菜单 *");printf("\n\t\t*******************************************");printf("\n\n\t\t\t请输入您的选择:");}//录入信息函数void Add(List L){Position TmpCell;int number;char n[20];printf("\n请输入所要创建的职工号: ");//提示输入职工号scanf("%d",&number); if(!IsLast(FindNumPrevious(number,L),L)) //连续调用 职工号前驱指针查找函数 判断链尾函数,判断该职工号是否已存在{printf("\n职工号 %d 已存在!!!\n\n",number);TurnBack(); //调用返回上一菜单函数return; //退出并返回上一级菜单}printf("\n请输入该职工的姓名: "); //保存职工姓名scanf("%s",n); if(!IsLast(FindNamePrevious(n,L),L))//连续调用 职工姓名前驱指针查找函数 判断链尾函数,判断该职工姓名是否已存在{printf("\n职工姓名 %s 已存在!!!\n\n",n);TurnBack(); //调用返回上一菜单函数return; //退出并返回上一级菜单}TmpCell=(Position)malloc(sizeof(struct Employee)); //创建新结点if(TmpCell==NULL){printf("\n添加失败,内存不足!!!\n\n"); //添加失败,提示内存不足system("pause"); //暂停屏幕显示return; //返回上一级菜单}TmpCell->num=number; //保存职工号strcpy(TmpCell->name,n); //保存姓名printf("\n请输入该职工的工作部门: "); //保存工作部门scanf("%s",TmpCell->department);printf("\n请输入该职工的职称: "); //保存职称scanf("%s",TmpCell->Title); printf("\n请输入该职工的入厂时间(格式为:年/月/日): "); //保存入厂时间scanf("%s",TmpCell->time);printf("\n请输入该职工的工资(单位:元): "); //保存工资scanf("%d",&TmpCell->money); TmpCell->Next=L->Next; //将结点TmpCell插入到链表中L->Next=TmpCell; printf("\n职工 %s 的信息创建成功!!!\n",TmpCell->name); //提示创建成功Save(L);//调用 信息保存函数TurnBack(); //调用 返回上一菜单函数return;//退出并返回上一级菜单}//显示菜单void ViewMeun() {printf("\n\t\t显示信息菜单");printf("\n\t\t********************************************");printf("\n\t\t* 1、显示职工信息*");printf("\n\t\t* 2、显示部门信息 *");printf("\n\t\t* 3、返回到主菜单*");printf("\n\t\t********************************************");printf("\n\n\t\t\t请输入您的选择:");}//信息显示函数void View(List L) {while(1){char a;system("cls"); //实现清屏ViewMeun(); //调用显示菜单fflush(stdin); //清除键盘缓冲区a=Test1(getchar(),'1','4');//调用菜单输入检测函数switch(a){case '1':system("cls"); ViewNum(L); break; //显示职工信息case '2':system("cls"); ViewDepartment(L); break; //显示部门信息case '3':return;}}}//职工号显示函数void ViewNum(List L) {Position P;int number;printf("\n请输入所要查询的职工号: ");scanf("%d",&number);P=FindNumPrevious(number,L); //调用职工号前驱指针查找函数,获得所需显示结点的前一结点if(IsLast(P,L)==1)//判断是否存在该员工printf("\n无职工号为 %d 的员工!!!\n\n",number);elsePrintEmployee(P->Next);//调用职工信息打印函数TurnBack(); //调用返回上一菜单函数return;//返回上一菜单}//部门信息显示函数void ViewDepartment(List L){Position P;PtrToTitle P1,L1;char c[20];int num,money;L1=NULL;L1=MakeEmptyTitle(L1); //调用职称链表创建函数num=money=0;printf("请输入所要查询的部门名称: ");scanf("%s",c);P=L->Next;while(P!=NULL&&strcmp(c,P->department)!=0)P=P->Next;if(P==NULL){printf("\n无名称为 %s 的部门\n\n",c);TurnBack();//调用返回上一菜单函数return;}printf("\n该部门职工信息如下:\n");printf("- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");printf(" 职工号 姓名 工作部门职称入厂时间 工资\t\n"); printf("- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");P=L->Next;while(P!=NULL){if(strcmp(c,P->department)==0){printf(" %-d %-s %-s %-s %-s%-d\n",P->num,P->name,P->department,P->Title,P->time,P->money);L1=InsertTitle(P->Title,L1);num++;money+=P->money;}P=P->Next;}printf("\n\n- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");printf("该部门的统计情况如下:\n 总人数为: %d 人\n 平均工资为: %.2f 元\n",num,(float)money/num);P1=L1->Next;while(P1!=NULL){printf(" 职称为 %s 的共: %d 人\n",P1->title,P1->num);P1=P1->Next;}putchar('\n');TurnBack(); //调用返回上一菜单函数return;//退出并返回上一级菜单} //文件函数//初始化函数List Init(List L) {FILE *fp; //文件指针Position TmpCell;int num=0;if((fp=fopen("职工信息.txt","r+"))==NULL)//打开"职工信息.txt"文本文件{printf("\n\t\t无法打开文件或文件不存在\n"); //提示错误printf("\n\t\t正在尝试创建新文件....\n");fp=fopen("职工信息.txt","w"); //创建"职工信息.txt"文本文件if((fp=fopen("职工信息.txt","r+"))==NULL) //再次打开判断是否成功{printf("\t\t文件创建失败!!!\n");system("pause"); //暂停屏幕显示return NULL;}}fp=fopen("职工信息.txt","r+"); //以只读的方式打开"职工信息.txt"文本文件L=MakeEmpty(L); //创建链表,以便存储文本文件中的信息while(1) //将磁盘中的信息输出到内存中{TmpCell=(Position)malloc(sizeof(struct Employee)); //创建新结点if(TmpCell==NULL){printf("文件信息读取失败,系统内存不足!!!\n"); //添加失败,提示内存不足system("pause"); //暂停屏幕显示return NULL;//返回上一级菜单}if(fscanf(fp,"%d %s %s %s %s %d",&TmpCell->num,TmpCell->name,TmpCell->department,TmpCell->Title,TmpCell->time,&TmpCell->money)<0) break; //将文件信息写入内存TmpCell->Next=L->Next;//将结点TmpCell插入到链表中L->Next=TmpCell; num++;} printf("\n\t\t职工信息读取完成!!!\n");printf("\n\t\t目前共有 %d 名职工信息\n",num);fclose(fp);//关闭文件return L;}//信息保存函数 void Save(List L) {FILE *fp; //文件指针Position P;L=Sort(L); //调用链表冒泡排序函数P=L;if((fp=fopen("职工信息.txt","w+"))==NULL) //打开"职工信息.txt"文本文件{printf("无法打开文件!!!\n");system("pause"); //暂停屏幕显示return;}fp=fopen("职工信息.txt","w+"); //以读写的方式打开"职工信息.txt"文本文件while(P->Next!=NULL) //将内存中的数据输出到磁盘中{P=P->Next; //信息从第一个有效结点开始保存,循环指向下一个有效结点if(fprintf(fp,"%d %s %s %s %s %d\n",P->num,P->name,P->department,P->Title,P->time,P->money)<0) break; //向文件写入信息}printf("\n职工信息保存成功!!!\n\n");fclose(fp);return;}//修改菜单函数void ModMeun() {printf("\n\t\t 职工修改菜单");printf("\n\t\t********************************************");printf("\n\t\t* 1、根据查询职工号修改 *");printf("\n\t\t* 2、返回到主菜单*");printf("\n\t\t********************************************");printf("\n\n\t\t\t请输入您的选择:");}//信息修改函数void Mod(List L) {while(1){char a;Position P;system("cls");//实现清屏ModMeun(); //调用修改菜单fflush(stdin);//清除键盘缓冲区a=Test1(getchar(),'1','3'); //调用菜单输入检测函数switch(a){case '1'://职工号修改{int number;system("cls"); printf("\n请输入所要修改的职工信息的职工号: ");scanf("%d",&number);P=FindNumPrevious(number,L); //调用职工号前驱指针查找函数,获得所需显示结点的前一结点if(IsLast(P,L)==1)//判断是否存在该员工{printf("\n无职工号为 %d 的员工!!!\n\n",number);TurnBack(); //调用返回上一菜单函数}elseMod1(P->Next,L);//调用修改的部分函数break; //返回上一菜单}case '2':return;}}}//修改的部分菜单void ModMeun1() {printf("\n\t\t 所要修改的部分");printf("\n\t\t********************************************");printf("\n\t\t* 1、职工号 *");printf("\n\t\t* 2、职工姓名 *");printf("\n\t\t* 3、返回上一菜单*");printf("\n\t\t********************************************");printf("\n\n\t\t\t请输入您的选择:");}//修改的部分函数 void Mod1(Position P,List L){while(1){char a;PrintEmployee(P);//调用职工信息打印函数ModMeun1(); //调用修改菜单fflush(stdin);//清除键盘缓冲区a=Test1(getchar(),'1','7'); //调用菜单输入检测函数switch(a){case '1': system("cls"); ModNum(P,L); break; //职工号修改case '2': system("cls"); ModName(P,L); break; //职工姓名修改case '3': return;}}}//职工号修改函数void ModNum(Position P,List L){int b; printf("\n请输入新的职工号: "); scanf("%d",&b); if(!IsLast(FindNumPrevious(b,L),L))//连续调用 职工号前驱指针查找函数 判断链尾函数,判断该职工号是否已存在printf("\n职工号 %d 已存在!!!\n\n",b);else{P->num=b; Save(L); //调用信息保存函数}TurnBack();//调用返回上一菜单函数return; //返回上一级菜单并退出}//职工姓名修改函数void ModName(Position P,List L) {char c[20]; printf("\n请输入新的职工姓名: "); scanf("%s",c); if(!IsLast(FindNamePrevious(c,L),L))//连续调用 职工姓名前驱指针查找函数 判断链尾函数,判断该职工姓名是否已存在printf("\n职工姓名 %s 已存在!!!\n\n",c);else{strcpy(P->name,c); Save(L); //调用信息保存函数}TurnBack();//调用返回上一菜单函数return; //返回上一级菜单并退出}//职工号删除函数void DeleteNum(List L) {Position P,TmpCell;int number;printf("\n请输入所要删除的职工信息的职工号: ");scanf("%d",&number);P=FindNumPrevious(number,L); //调用职工号前驱指针查找函数,获得所需显示结点的前一结点if(IsLast(P,L)==1)//判断是否存在该员工printf("\n无职工号为 %d 的员工!!!\n\n删除失败!!!\n\n",number);else{PrintEmployee(P->Next);//调用职工信息打印函数fflush(stdin); //清除键盘缓冲区printf("\n是否确认要删除?回复'Y'/'N'\n");if(getchar()=='Y'){TmpCell=P->Next;P->Next=TmpCell->Next; free(TmpCell);printf("\n删除成功!!!\n\n");Save(L); //调用信息保存函数}}TurnBack(); //调用返回上一菜单函数return;//退出并返回上一级菜单}//职工信息打印函数void PrintEmployee(Position P){printf("\n该职工信息如下:\n");printf("- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");printf(" 职工号 姓名工作部门职称 入厂时间工资\n"); printf("- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");printf(" %-d %-s %-s %-s %-s %-d\n",P->num,P->name,P->department,P->Title,P->time,P->money);printf("\n\n- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\n");}//菜单输入检测函数char Test1(char a,char b,char c) {while(a<b||a>c){printf("\n\t\t\t输入错误,请重新输入: ");fflush(stdin); //清除键盘缓冲区a=getchar();}return a;}//返回上一菜单函数void TurnBack() {printf("按回车键返回上一菜单...");fflush(stdin); //清除键盘缓冲区getchar(); //读取任意按键值system("cls"); //实现清屏}

四、运行页面展示

1、注册登录界面

2、选择菜单页面

3、功能菜单界面

五、总结与收获

在本次项目中,我用C语言编写了一个职工信息管理系统,实现了注册登录、增删改查操作、以及显示信息功能。通过这个项目,我收获了以下几点:

一是掌握了C语言的基本语法和数据结构,如变量、常量、运算符、表达式、控制流、函数、数组、指针、结构体等。我学会了如何定义和使用这些元素,以及如何解决一些常见的编程问题和错误。二是熟悉了文件操作的方法和技巧,如打开、关闭、读写、追加等。我学会了如何用文件存储和读取职工信息,以及如何用二进制和文本格式进行文件转换。三是理解了模块化编程的思想和好处,如封装、抽象、复用等。我学会了如何将程序分为多个模块,每个模块负责一个功能,然后通过接口进行通信和协作。这样可以提高程序的可读性、可维护性和可扩展性。四是探索了一些高级的编程技巧和特性,如动态内存分配、链表、排序算法等。我学会了如何用这些技巧和特性优化程序的性能和功能,以及如何避免一些潜在的内存泄漏和逻辑错误。五是体验了软件开发的完整过程,从需求分析、设计、编码、测试、到部署和使用。我学会了如何根据用户需求设计程序的功能和界面,如何编写规范和清晰的代码,如何进行有效的调试和测试,以及如何给用户提供友好和方便的操作指南。

总之,通过这个项目,我不仅锻炼了我的编程能力和逻辑思维,也拓展了我的知识面和视野。我感受到了C语言的强大和灵活,也感受到了编程的乐趣和挑战。我相信这个项目对我的学习和成长有很大的帮助,也为我今后的编程之路打下了坚实的基础。

最后我要说的是,本次课设能够成功完成,不仅仅是因为自己的努力,还有同学以及老师的帮助。本次课设收获的不仅是代码实现系统的能力,还有多方面的能力与经验,是一次受益匪浅的学习过程。

以"穷途总是非末路,沧海绝境见青山。"共勉。

Code_流苏(CSDN)(一个喜欢古诗词和编程的Coder😊)

如果对大家有帮助的话,希望大家能多多点赞+关注!这样我动力会更足哦! ღ( ´・ᴗ・` )比心

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。