赞
踩
数据结构C/C++ 职工信息管理系统
本文还是使用较老的 VC++6.0
这里推荐可以使用小熊猫C++ 用的还是比较舒服方便的,下头完整代码里会有区别介绍。
系统还是较为简陋,会有一些bug,欢迎各位大佬进行改进。
系统任务描述如下:
设有一组职工数据,每个职工记录包含职工编号(no)、姓名(name)、部门号(depno)和工资数(salary)。设计一个程序完成以下功能:
(1)建表。从键盘输入职工记录,并建立一个带头结点的单链表L。
(2)输入。添加一个职工信息。
(3)输出。输出全部职工信息。
(4)排序。按职工编号no所有职工记录进行递增排序,并输出所有职工记录。
(5)排序。按部门号no所有职工记录进行递增排序,并输出所有职工记录。
(6)排序。按工资数salary所有职工记录进行递增排序,并输出所有职工记录。
(7)删除。删除指定职工编号的职工记录。
(8)删除。删除职工链表L中的全部记录。
(9)存储后退出。将单链表中的全部结点数据存储到职工文件中,然后退出程序运行过程。
1. 职工信息管理系统功能模块结构图和职工信息结构图:
2. 菜单功能
- void menu()
- {
- system("cls");//清屏
- system("color 00b");//设置为蓝色
- printf(" **********欢迎使用职工管理系统**************\n");
- printf(" 请输入如下命令执行相应功能\n");
- printf(" 【1】 添加一个职工信息\n");
- printf(" 【2】 输出全部职工信息\n");
- printf(" 【3】 按职工号排序\n");
- printf(" 【4】 按部门号排序\n");
- printf(" 【5】 按工资数排序\n");
- printf(" 【6】 删除指定职工编号记录\n");
- printf(" 【7】 删除全部职工记录 \n");
- printf(" 【8】 清屏\n");
- printf(" 【9】 储存信息并退出\n");
- printf(" 【-1】 退出程序\n");
- printf(" ********************************************\n");
- }
使用malloc函数为头节点分配内存,并强制转化为结点指针类型,并赋值给头指针。接下来看内存分配是否成功。如果头指针不为空,则令头结点next域指向空。否则,它会打印错误消息 "内存不足!" 并返回-1表示初始化失败。
- int Initlist(LinkNode *&L)
- {
- L=(LinkNode *)malloc(sizeof(LinkNode));
- if(L!=NULL)
- {
- L->next=NULL;
- return 1;
- }
- else
- {
- printf("内存不足!\n");
- return 0;
- }
- }
利用头插法建表,重复读入数据,生成新结点,将读入数据存放到新结点的数据域中,然后将新结点插入到当前链表的表头结点之后,直至读入结束标志为止。
若链表中存在与新结点中相同的职工号,打印“录入失败提示:此职工号已经存在!”的提示信息,表示插入失败,并释放新结点。反之,打印“录入成功!”的提示信息,表示插入成功。
- int CreateListF(LinkNode *&L)
- {
- LinkNode *q=(LinkNode *)malloc(sizeof(LinkNode));
- printf("请输入职工号(数字):");
- scanf("%d",&q->w.no);
- LinkNode *s=L->next;
- while(s)
- {
- if(s->w.no==q->w.no)
- {
- free(q);
- printf("录入失败提示:此职工号已经存在!\n");
- return -1;
- }
- s=s->next;
- }
- printf("请输入职工姓名(文字):");
- scanf("%s",&q->w.name);
- printf("请输入职工部门号(数字):");
- scanf("%d",&q->w.departno);
- printf("请输入职工工资数(数字):");
- scanf("%d",&q->w.salary);
- q->next=L->next;
- L->next=q;
- printf("录入成功!\n");
- return 1;
- }
使用while循环遍历链表,如果链表非空,则执行以下步骤。输出当前节点的职工信息,包括职工号、姓名、部门号、工资等。将节点的指针移动到链表的下一个节点。循环执行步骤2~3,直到链表为空为止。输出显示完毕的信息。
- void show(LinkNode *L)
- {
- menu();
- printf("浏览职工信息\n");
- printf("职工号\t姓名\t部门号\t工资\t\n");
- while(L->next!=NULL)
- {
- printf("%d\t%s\t%d\t%d\t\n",L->next->w.no,L->next->w.name,L->next->w.departno,L->next->w.salary);
- L=L->next;
- }
- printf("显示完毕!\n");
- }
构建一个有序的结点序列,其相关数据域按递增排序,从头节点遍历有序序列,与无序序列头节点数据域一一比较,取出结点并将其放在有序序列中合适的位置上,直到无序序列中没有元素。
若要以部门号或薪资号进行递增排序,只需更改结点中结构体的成员即可。
职工号递增:
- LinkNode nolist(LinkNode *&L)
- {
- LinkNode *p=L->next;
- LinkNode *r=p->next;
- LinkNode *q;
- LinkNode *pre;
- p->next=NULL;
- p=r;
- while(p!=NULL)
- {
- r=p->next;
- q=L;
- while(q->next!=NULL&&q->next->w.no<p->w.no)
- {
- q=q->next;
- }
- pre=q;
- p->next=pre->next;
- pre->next=p;
- p=r;
- }
- return *L;
- }
部门号递增:
- LinkNode depnolist(LinkNode *&L)
- {
- LinkNode *p=L->next;
- LinkNode *r=p->next;
- LinkNode *q;
- LinkNode *pre;
- p->next=NULL;
- p=r;
- while(p!=NULL)
- {
- r=p->next;
- q=L;
- while(q->next!=NULL&&q->next->w.departno<p->w.departno)
- {
- q=q->next;
- }
- pre=q;
- p->next=pre->next;
- pre->next=p;
- p=r;
- }
- return *L;
- }
工资递增:
- LinkNode salarylist(LinkNode *&L)
- {
- LinkNode *p=L->next;
- LinkNode *r=p->next;
- LinkNode *q;
- LinkNode *pre;
- p->next=NULL;
- p=r;
- while(p!=NULL)
- {
- r=p->next;
- q=L;
- while(q->next!=NULL&&q->next->w.salary<p->w.salary)
- {
- q=q->next;
- }
- pre=q;
- p->next=pre->next;
- pre->next=p;
- p=r;
- }
- return *L;
- }
删除指定的员工
遍历链表,查找待删除职工号所在的节点。若找到,则保存该节点的指针q,并让节点k指向q的下一个节点。使用free函数释放q指向的节点空间,并输出删除成功的信息。若遍历完整个链表仍未找到待删除的职工号,则输出删除失败的信息。
- int deleteone(LinkNode *&L,int no)
- {
- menu();
- printf("正在按职工号删除职工信息\n");
- LinkNode *k=L;
- while(k->next!=NULL)
- {
- if(k->next->w.no==no)
- {
- LinkNode *q=k->next;
- k->next=q->next;
- free(q);
- printf("删除职工号%d成功!\n",no);
- return 1;
- }
- k=k->next;
- }
- printf("没有你输入的职工号!\n");
- return -1;
- }
删除全部员工
使用while循环遍历链表,如果链表非空,则执行以下步骤。保存链表头结点指向的节点q的指针,并让头结点指向q的下一个节点。释放q指向的节点空间。循环执行步骤2~3,直到链表为空为止。
- void deleteall(LinkNode *&L)
- {
- while(L->next!=NULL)
- {
- LinkNode *q=L->next;
- L->next=L->next->next;
- free(q);
- }
- }
定义文件指针fp,并使用fopen函数打开文件work.txt,如果打开失败,则输出提示信息,函数结束。使用while循环遍历链表,如果链表非空,则执行以下步骤。
将当前节点存储的职工信息写入文件,使用fwrite函数,并向其传递3个参数:待写入的数据地址、每个数据单元的字节数、待写入的数据单元数量,函数的返回值表示成功写入的数据单元数量。将节点的指针移动到链表的下一个节点,并统计写入的节点数量n。循环执行步骤3~4,直到链表为空为止。使用fclose函数关闭文件。
使用free函数释放链表头结点的内存空间。输出写入文件的职工信息数量,或者提示没有任何记录写入文件。
代码生成的work.txt文件与C++编译文件在相同路径
- void SaveFile(LinkNode *L) {
- LinkNode *q = L->next;
- int n = 0;
- FILE *fp;
- if ((fp = fopen("work.txt", "w")) == NULL) {
- printf("提示:不能创建文件\n");
- return;
- } else {
- printf("保存成功\n");
- }
- fprintf(fp, "职工号\t姓名\t部门号\t薪资\n");
- fprintf(fp, "----------------------------------------------------\n");
- while (q != NULL) {
- fprintf(fp, "%d\t%s\t%d\t%d\n", q->w.no, q->w.name, q->w.departno, q->w.salary);
- q = q->next;
- n++;
- }
- fclose(fp);
- if (n > 0)
- printf("%d个职工记录写入work.txt文件\n", n);
- else
- printf("没有任何职工记录写入work.txt文件\n");
- free(L);
- }
查询主要还是遍历链表
利用strcmp函数查看字符串是否匹配
3.9原理类似
- void searchname(LinkNode *L)
- {
- int flag = 0;
- LinkNode *p = L->next;
- char num[5];
- printf("请输入要查找的职工姓名: ");
- scanf("%s", num);
- while (p != NULL)
- {
- if (strcmp(p->w.name, num) == 0)
- {
- flag = 1;
- printf("职工信息为:\n");
- printf("%d\t%s\t%d\t%d\n", p->w.no, p->w.name, p->w.departno, p->w.salary);
- break;
- }
- p = p->next;
- }
- if (flag == 0)
- {
- printf("姓名为%s的职工不存在!\n", num);
- }
- }
- void searchno(LinkNode *L)
- {
- int flag = 0;
- int no;
- LinkNode *p = L->next;
- char num[5];
- printf("请输入要查找的职工编号: ");
- scanf("%s", num);
- sscanf(num, "%d", &no);
- while (p != NULL)
- {
- if (p->w.no == no)
- {
- flag = 1;
- printf("职工信息为:\n");
- printf("职工号: %d\t姓名: %s\t部门号: %d\t薪资: %d\n",
- p->w.no, p->w.name, p->w.departno, p->w.salary);
- break;
- }
- p = p->next;
- }
- if (flag == 0)
- {
- printf("编号为%s的职工不存在!\n", num);
- }
- }
这里直接将代码放到vc++6.0的c++文件就行。
要是使用小熊猫C++的话注意
void main() 改成 int main()
scanf("%s",%q->w.name) 改成 scanf("%s",q->w.name);
下头的文件保存就会保存到与建立的c++文件相同的路径。
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <malloc.h>
- struct Worker {
- int no;
- char name[8];
- int departno; //部门
- int salary;
- };
- typedef struct LNode {
- Worker w;
- LNode *next;
- } LinkNode;
-
- void menu() {
-
- system("cls");//清屏
- printf(" **********欢迎使用职工管理系统**************\n");
- printf(" 请输入如下命令执行相应功能\n");
- printf(" 【1】 添加一个职工信息\n");
- printf(" 【2】 输出全部职工信息\n");
- printf(" 【3】 按职工号排序\n");
- printf(" 【4】 按部门号排序\n");
- printf(" 【5】 按工资数排序\n");
- printf(" 【6】 删除指定职工编号记录\n");
- printf(" 【7】 删除全部职工记录 \n");
- printf(" 【8】 清屏\n");
- printf(" 【9】 储存信息并退出\n");
- printf(" 【10】 按职工姓名查询\n");
- printf(" 【11】 按职工编号查询\n");
- printf(" 【-1】 退出程序\n");
- printf(" ********************************************\n");
- }
-
-
- int Initlist(LinkNode *&L)
- {
- L=(LinkNode *)malloc(sizeof(LinkNode));
- if(L!=NULL)
- {
- L->next=NULL;
- return 1;
- }
- else
- {
- printf("内存不足!\n");
- return 0;
- }
- }
-
-
- void SaveFile(LinkNode *L) {
- LinkNode *q = L->next; // 从第一个数据节点开始遍历
- int n = 0; // 记录写入的职工记录数量
- FILE *fp;
- if ((fp = fopen("work.txt", "w")) == NULL) {
- printf("提示:不能创建文件\n");
- return;
- } else {
- printf("保存成功\n");
- }
- fprintf(fp, "职工号\t姓名\t部门号\t薪资\n");
- fprintf(fp, "----------------------------------------------------\n");
- while (q != NULL) {
- // 将职工信息写入文件
- fprintf(fp, "%d\t%s\t%d\t%d\n", q->w.no, q->w.name, q->w.departno, q->w.salary);
- q = q->next; // 移动到下一个节点
- n++;
- }
- fclose(fp);
- if (n > 0)
- printf("%d个职工记录写入work.txt文件\n", n);
- else
- printf("没有任何职工记录写入work.txt文件\n");
- free(L);
- }
-
- /*录入职工信息*/ //采用头插法
- int CreateListF(LinkNode *&L)
- {
- LinkNode *q=(LinkNode *)malloc(sizeof(LinkNode));
- printf("请输入职工号(数字):");
- scanf("%d",&q->w.no);
- LinkNode *s=L->next;
- while(s)
- {
- if(s->w.no==q->w.no)
- {
- free(q);
- printf("录入失败提示:此职工号已经存在!\n");
- return -1;
- }
- s=s->next;
- }
- printf("请输入职工姓名(文字):");
- scanf("%s",q->w.name);
- printf("请输入职工部门号(数字):");
- scanf("%d",&q->w.departno);
- printf("请输入职工工资数(数字):");
- scanf("%d",&q->w.salary);
- q->next=L->next;
- L->next=q;
- printf("录入成功!\n");
- return 1;
- }
- //职工号排序
- LinkNode nolist(LinkNode *&L)
- {
- LinkNode *p=L->next;
- LinkNode *r=p->next;
- LinkNode *q;
- LinkNode *pre;
- p->next=NULL;
- p=r;
- while(p!=NULL)
- {
- r=p->next;
- q=L;
- while(q->next!=NULL&&q->next->w.no<p->w.no)
- {
- q=q->next;
- }
- pre=q;
- p->next=pre->next;
- pre->next=p;
- p=r;
- }
- return *L;
- }
- //部门号排序
- LinkNode depnolist(LinkNode *&L)
- {
- LinkNode *p=L->next;
- LinkNode *r=p->next;
- LinkNode *q;
- LinkNode *pre;
- p->next=NULL;
- p=r;
- while(p!=NULL)
- {
- r=p->next;
- q=L;
- while(q->next!=NULL&&q->next->w.departno<p->w.departno)
- {
- q=q->next;
- }
- pre=q;
- p->next=pre->next;
- pre->next=p;
- p=r;
- }
- return *L;
- }
- //工资排序
- LinkNode salarylist(LinkNode *&L)
- {
- LinkNode *p=L->next;
- LinkNode *r=p->next;
- LinkNode *q;
- LinkNode *pre;
- p->next=NULL;
- p=r;
- while(p!=NULL)
- {
- r=p->next;
- q=L;
- while(q->next!=NULL&&q->next->w.salary<p->w.salary)
- {
- q=q->next;
- }
- pre=q;
- p->next=pre->next;
- pre->next=p;
- p=r;
- }
- return *L;
- }
- //按职工号删除职工信息(已修改)
- int deleteone(LinkNode *&L,int no)
- {
- menu();
- printf("正在按职工号删除职工信息\n");
- LinkNode *k=L;
- while(k->next!=NULL)
- {
- if(k->next->w.no==no)
- {
- LinkNode *q=k->next;
- k->next=q->next;
- free(q);
- printf("删除职工号%d成功!\n",no);
- return 1;
- }
- k=k->next;
- }
- printf("没有你输入的职工号!\n");
- return -1;
- }
- //删除全部员工记录(修改已正常)
- void deleteall(LinkNode *&L)
- {
- while(L->next!=NULL)
- {
- LinkNode *q=L->next;
- L->next=L->next->next;
- free(q);
- }
- }
- //浏览职工信息
- void show(LinkNode *L)
- {
- menu();
- printf("浏览职工信息\n");
- printf("职工号\t姓名\t部门号\t工资\t\n");
- while(L->next!=NULL)
- {
- printf("%d\t%s\t%d\t%d\t\n",L->next->w.no,L->next->w.name,L->next->w.departno,L->next->w.salary);
- L=L->next;
- }
- printf("显示完毕!\n");
- }
-
- //查询
- void searchname(LinkNode *L) {
- int flag = 0;
- LinkNode *p = L->next;
- char num[5];
- printf("请输入要查找的职工姓名: ");
- scanf("%s", num);
- while (p != NULL)
- {
- if (strcmp(p->w.name, num) == 0)
- {
- flag = 1;
- printf("职工信息为:\n");
- printf("%d\t%s\t%d\t%d\n", p->w.no, p->w.name, p->w.departno, p->w.salary);
- break;
- }
- p = p->next;
- }
- if (flag == 0)
- {
- printf("姓名为%s的职工不存在!\n", num);
- }
- }
- void searchno(LinkNode *L)
- {
- int flag = 0;
- int no;
- LinkNode *p = L->next;
- char num[5];
- printf("请输入要查找的职工编号: ");
- scanf("%s", num);
- sscanf(num, "%d", &no);
- while (p != NULL)
- {
- if (p->w.no == no)
- {
- flag = 1;
- printf("职工信息为:\n");
- printf("职工号: %d\t姓名: %s\t部门号: %d\t薪资: %d\n",
- p->w.no, p->w.name, p->w.departno, p->w.salary);
- break;
- }
- p = p->next;
- }
- if (flag == 0)
- {
- printf("编号为%s的职工不存在!\n", num);
- }
- }
-
- int main() {
- int ord = 0;
- int no;
- LinkNode *L;
- if (!(Initlist(L)))
- exit(0);
- while (ord != -1) {
- switch (ord) {
- case 0:
- menu();
- break;
- case 1:
- CreateListF(L);
- break;
- case 2:
- show(L);
- break;
- case 3:
- nolist(L);
- show(L);
- printf("按职工号排列成功!\n");
- break;
- case 4:
- depnolist(L);
- show(L);
- printf("按部门号排列成功!\n");
- break;
- case 5:
- salarylist(L);
- show(L);
- printf("按工资排列成功!\n");
- break;
- case 6:
- printf("请输入要删除的职工号:");
- scanf("%d", &no);
- deleteone(L, no);
- printf("删除成功!\n");
- //show(L);
- break;
- case 7:
- deleteall(L);
- show(L);
- printf("记录为空\n");
- printf("已经删除全部记录!\n");
- break;
- case 8:
- default:
- menu();
- break;
- case 9:
- SaveFile(L);
- exit(0);
- case 10:
- searchname(L);
- break;
- case 11:
- searchno(L);
- break;
- }
- printf("请输入操作命令数字:\n");
- scanf("%d", &ord);
- }
- free(L);
- }
-
初始界面:
进行插入功能:
进行输出功能:
进行删除功能:删除指定员工和删除全部员工
进行排序功能:以职工号,职工部门号,职工工资信息排序
进行存储功能:
通过设计职工信息管理系统,我对单链表这个数据结构更加熟悉。单链表可以通过指针进行节点的连接,从而形成一个链式结构,每个节点存储一个员工的信息,如工号、姓名、部门、工资等。首先是节点的定义,每个节点存储一个员工的信息,通过指针连接下一个节点。接着是链表的插入、删除和查找操作,可以通过指针来实现节点之间的连接和数据的读取。最后是利用文件操作实现了职工信息的存储。也知道了链表的头节点需要单独处理,通常不存储数据信息。对链表的操作也需要考虑边界条件,如链表为空、插入位置超出范围等。
通过前面的实验学习我了解到单链表,双链表,栈,队列,的逻辑结构都是一对一的线性结构,学习并掌握了数据结构相关的基本概念、分类、实现方法和应用场景,并通过实验实际操作加深了对数据结构的理解。例如,栈和队列常用于程序调试和嵌套结构的处理;链表通常用于动态内存分配和实现复杂的数据结构;此外,也学习到了各种各样的排序算法,但还是没有十全十美的算法
数据结构是基础的一门课,最初接触是对一些思想可能只是生硬的记忆,随着学习的深入逐渐领悟了很多。数据结构广泛应用于程序设计、数据库、网络等领域。总之,学习数据结构是计算机科学中的重要部分,是提高编程技能和实现复杂程序的必备基础之一。
感谢老师在学习中给予的帮助与指导,让我深入地了解数据结构的原理和实现。
C语言程序设计 利用文件保存数据_save函数在c语言中有关文件的用法-CSDN博客
https://blog.csdn.net/qq_31790997/article/details/90114169
数据结构《职工管理系统》_提供排序功能,可按照多种关键字对职工进行排序。要求按照“部门号”(“部门号”相-CSDN博客
https://www.bilibili.com/video/BV1et4y197Ud/?spm_id_from=333.999.0.0
希望对你有所帮助
记录:
2024/6/24 对文件存储进行了修改,并修改小熊猫C++运行内容的阐述。
原3.7文件存储错误代码,引用有问题。
- void SaveFile(LinkNode *L)
- {
- LinkNode *q=L->next;
- int n=0;
- FILE *fp;
- if ((fp=fopen("work.txt","wb+"))==NULL)
- {
- printf(" 提示:不能创建文件work.txt\n");
- return;
- }
- while (q!=NULL)
- {
- fwrite(&q->w,sizeof(Worker),1,fp);
- q=q->next;
- n++;
- }
- fclose(fp);
- free(L);
- if (n>0)
- printf("%d个职工记录写入work.txt文件\n",n);
- else
- printf("没有任何职工记录写入work.txt文件\n");
- }
6.27 添加查询功能
设计图未显示
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。