03职工管理系统

职工管理系统

1、管理系统需求

职工管理系统可以用来管理公司内所有员工的信息

本教程主要利用C++来实现一个基于多态的职工管理系统

公司中职工分为三类:普通员工、经理、老板,显示信息时,需要显示职工编号、职工姓名、职工岗位、以及职责

普通员工职责:完成经理交给的任务

经理职责:完成老板交给的任务,并下发任务给员工

老板职责:管理公司所有事务

管理系统中需要实现的功能如下:

  • 退出管理程序:退出当前管理系统
  • 增加职工信息:实现批量添加职工功能,将信息录入到文件中,职工信息为:职工编号、姓名、部门编号
  • 显示职工信息:显示公司内部所有职工的信息
  • 删除离职职工:按照编号删除指定的职工
  • 修改职工信息:按照编号修改职工个人信息
  • 查找职工信息:按照职工的编号或者职工的姓名进行查找相关的人员信息
  • 按照编号排序:按照职工编号,进行排序,排序规则由用户指定
  • 清空所有文档:清空文件中记录的所有职工信息 (清空前需要再次确认,防止误删)

系统界面效果图如下:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-yybfg02Q-1675440469277)(null)]

需根据用户不同的选择,完成不同的功能!

2、创建项目

创建项目步骤如下:

  • 创建新项目
  • 添加文件

2.1 创建项目

2.2 添加文件

3、创建管理类

​ 管理类负责的内容如下:

  • 与用户的沟通菜单界面
  • 对职工增删改查的操作
  • 与文件的读写交互

3.1创建文件

在头文件和源文件的文件夹下分别创建workerManager.h 和 workerManager.cpp文件

3.2 头文件实现

在workerManager.h中设计管理类

此处的workerManager类函数为分文件类外定义,相关知识点可见:类外实现

C++头文件相关知识点:ifndef使用

头文件实现类的声明

#ifndef与#pagram

代码如下:

#ifndef WorkerManager_H	//防止头文件的重复包含和编译 一般名字设置为文件名大写加上H,C++ 5th推荐加下划线6th没有
#define WorkerManager_H
//职工类
class WorkerManager {
public:
	//构造函数
	WorkerManager();
	//析构函数
	~WorkerManager();
};
#endif
//VS默认#pragma once但是使用了支持更加广泛的ifndef

3.3 源文件实现

在workerManager.cpp中将构造和析构函数空实现补全

#include"workerManager.h"
#include<iostream>
WorkerManager::WorkerManager() {

}
WorkerManager::~WorkerManager() {

}

至此职工管理类以创建完毕

4、菜单功能

功能描述:与用户的沟通界面

4.1 添加成员函数

在管理类workerManager.h中添加成员函数 void Show_Menu();

4.2 菜单功能实现

在管理类workerManager.cpp中实现 Show_Menu()函数

#include"workerManager.h"
#include<iostream>
//using namespace std;//尽量少使用,如果使用放在所有include之后
//using std::cout;
WorkerManager::WorkerManager() {

}
WorkerManager::~WorkerManager() {

}

//显示菜单
void WorkerManager::showMenu() {
	std::cout << "********************************************" << std::endl;
	std::cout << "*********  欢迎使用职工管理系统! **********" << std::endl;
	std::cout << "*************  0.退出管理程序  *************" << std::endl;
	std::cout << "*************  1.增加职工信息  *************" << std::endl;
	std::cout << "*************  2.显示职工信息  *************" << std::endl;
	std::cout << "*************  3.删除离职职工  *************" << std::endl;
	std::cout << "*************  4.修改职工信息  *************" << std::endl;
	std::cout << "*************  5.查找职工信息  *************" << std::endl;
	std::cout << "*************  6.按照编号排序  *************" << std::endl;
	std::cout << "*************  7.清空所有文档  *************" << std::endl;
	std::cout << "********************************************" << std::endl;
	std::cout << std::endl;
}

4.3 测试菜单功能

在职工管理系统.cpp中测试菜单功能

代码:

#include<iostream>
#include "workerManager.h"

int main() {

	WorkerManager wm;

	wm.Show_Menu();

	system("pause");

	return 0;
}

5、退出功能

5.1 提供功能接口

在main函数中提供分支选择,提供每个功能接口

代码:

#include<iostream>
#include "workerManager.h"

int main() {
	WorkerManager wm;
	int choice = 0;//功能选择,默认为0
	while (true) {//菜单循环显示
		//展示菜单
		wm.showMenu();
		std::cout << "请输入您的选择:" << std::endl;
		std::cin >> choice;
		switch (choice) {//功能选择
		case 0://退出系统
			break;
		case 1://添加职工
			break;
		case 2://显示职工
			break;
		case 3://删除职工
			break;
		case 4://修改职工
			break;
		case 5://查找职工
			break;
		case 6://排序职工
			break;
		case 7://清空文件
			break;
		default://默认清屏显示菜单
			system("cls");
			break;
		}
	}
	system("pause");
	return 0;
}

5.2 实现退出功能

workerManager.h中提供退出系统的成员函数 void exitSystem();

workerManager.cpp中提供具体的功能实现

//退出程序
void WorkerManager::exitSystem() {
	std::cout << "欢迎下次使用" << std::endl;
	system("pause");
	exit(0);// 清理I/O缓冲区后再退出进程
}

5.3测试功能

在main函数分支 0 选项中,调用退出程序的接口

6、创建职工类

6.1 创建职工抽象类

职工的分类为:普通员工、经理、老板

将三种职工抽象到一个类(worker)中,利用多态管理不同职工种类

职工的属性为:职工编号、职工姓名、职工所在部门编号

职工的行为为:岗位职责信息描述,获取岗位名称

头文件文件夹下 创建文件worker.h 文件并且添加如下代码:

  • 因为是基类而且不需要实现,所以没有cpp文件
#ifndef WORK_H
#define WORK_H	
#include<iostream>
//职工抽象基类
class Work {
public:
	//显示职位信息
	virtual void showInfo() = 0;//纯虚数函数
	//获取岗位名称
	virtual std::string getDeptName() = 0;
public:
	int id;//职工编号
	std::string name;//职工姓名
	int deptId;//职工所在部门编号
};
#endif

6.2 创建普通员工类

普通员工类继承职工抽象类,并重写父类中纯虚函数

在头文件和源文件的文件夹下分别创建employee.h employee.cpp文件

employee.h中代码如下:

#ifndef EMPLOYEE_H
#define EMPLOYEE_H
#include "worker.h"
//普通员工类
class Employee:public Worker {
public:
	//构造函数
	Employee(int id, std::string name, int dId);
	//显示个人信息
	virtual void showInfo();//必须重写
	//获取职工岗位名称
	virtual std::string getDeptName();//必须重写
};
#endif

employee.cpp中代码如下:

#include "employee.h"

//构造函数
Employee::Employee(int id, std::string name, int dId) {
	this->id = id;
	this->name = name;
	this->deptId = dId;
}

//显示个人信息
void Employee::showInfo() {
	std::cout << "职工编号:" << this->id
		<< "\t职工姓名:" << this->name
		<< "\t岗位:" << this->getDeptName()
		<< "\t岗位职责:完成经理交代的任务" << std::endl;
}

//获取岗位名称
std::string Employee::getDeptName() {
	return std::string("员工");
}

6.3 创建经理类

经理类继承职工抽象类,并重写父类中纯虚函数,和普通员工类似

在头文件和源文件的文件夹下分别创建manager.hmanager.cpp文件

manager.h中代码如下:

#ifndef MANAGER_H
#define MANAGER_H
#include "worker.h"
//经理类
class Manager :public Worker {
	//构造函数
	Manager(int id, std::string name, int dId);
	//显示个人信息
	virtual void showInfo();
	//获取职工岗位名称
	virtual std::string getDeptName();
};
#endif

manager.cpp中代码如下:

#include "manager.h"
//经理类

//构造函数
Manager::Manager(int id, std::string name, int dId) {
	this->id = id;
	this->name = name;
	this->deptId = dId;
}

//显示个人信息
void Manager::showInfo() {
	std::cout << "职工编号:" << this->id
		<< "\t职工姓名:" << this->name
		<< "\t岗位:" << this->getDeptName()
		<< "\t岗位职责:完成老板交代的任务,下发任务给员工" << std::endl;
}

//获取岗位信息
std::string Manager::getDeptName() {
	return std::string("经理");
}

6.4 创建老板类

老板类继承职工抽象类,并重写父类中纯虚函数,和普通员工类似

在头文件和源文件的文件夹下分别创建boss.h boss.cpp文件

boss.h中代码如下:

#ifndef	BOSS_H
#define BOSS_H
#include"worker.h"
//老板类
class Boss :public Worker {
	//构造函数
	Boss(int id, std::string name, int dId);
	//显示个人信息
	virtual void getInfo();
	//获取职位信息
	virtual std::string getDeptName();
};
#endif

boss.cpp中代码如下:

#include"boss.h"
//老板类

//构造函数
Boss::Boss(int id, std::string name, int dId) {
	this->id = id;
	this->name = name;
	this->deptId = dId;
}

//显示个人信息
 void Boss::getInfo() {
	 std::cout << "职工编号:" << this->id
		 << "\t职工姓名:" << this->name
		 << "\t岗位:" << this->getDeptName()
		 << "\t岗位职责:管理公司所有事务" << std::endl;
}
 
 //获取职位信息
 std::string Boss::getDeptName() {
	 return std::string("总裁");
 }

6.5 测试多态

职工管理系统.cpp中添加测试函数,并且运行能够产生多态

测试代码如下:

#include<iostream>
#include "workerManager.h"	//职工类
#include"worker.h"			//职工抽象基类
#include"employee.h"		//员工类
#include"manager.h"			//管理类
#include"boss.h"			//老板类


//测试多态
void test() {
	Worker* worker = NULL;
	worker = new Employee(1, "张三", 1);
	worker->showInfo();
	delete worker;
	Worker* worker2 = NULL;
	worker2 = new Manager(2, "李四", 1);
	worker2->showInfo();
	delete worker2;
	Worker* worker3 = NULL;
	worker3 = new Boss(3, "王五", 1);
	worker3->showInfo();
	delete worker3;
}

测试成功后,测试代码可以注释保留,或者选择删除

7、添加职工

功能描述:批量添加职工,并且保存到文件中

7.1 功能分析

分析:

用户在批量创建时,可能会创建不同种类的职工

如果想将所有不同种类的员工都放入到一个数组中,可以将所有员工的指针维护到一个数组里

如果想在程序中维护这个不定长度的数组,可以将数组创建到堆区,并利用Worker **的指针维护

7.2 功能实现

WokerManager.h头文件中添加成员属性 代码:

#include "worker.h"	
//记录文件中的人数个数
	int m_EmpNum;

	//员工数组的指针
	Worker ** m_EmpArray;//定义指向数据为指针的指针

WorkerManager构造函数中初始化属性

WorkerManager::WorkerManager()
{
	//初始化人数
	this->m_EmpNum = 0;

	//初始化数组指针
	this->m_EmpArray = NULL;
}

workerManager.h中添加成员函数

	//增加职工
	void Add_Emp();

workerManager.cpp中实现该函数

#include "workerManager.h"	//职工类
#include"worker.h"			//职工抽象基类
#include"employee.h"		//员工类
#include"manager.h"			//管理类
#include"boss.h"			//老板类

//增加职工
void WorkerManager::addEmp() {
	std::cout << "请输入增加职工数量:";
	int addNum = 0;
	std::cin >> addNum;
	if (addNum > 0) {//输入数据合法
		//计算新空间大小
		int newSize = this->empNum + addNum;
		//开辟新空间
		Worker** newSpace = new Worker * [newSize];
		//将原有空间下内容转移到新空间中
		if (this->empArray != NULL) {//原有数据存在
			for (int i = 0; i < this->empNum; i++) {
				if (i < newSize) {//如果没有判断报错C6386 虽然似乎报错没有什么意义
					newSpace[i] = this->empArray[i];
				}
			}
		}
		//输入新数据
		for (int i = 0; i < addNum; i++) {
			int id;
			std::string name;
			int dId;
			//信息输入
			//编号
			std::cout << "请输入第" << i + 1 << "个职工编号:";
			std::cin >> id;
			//姓名
			std::cout << "请输入第" << i + 1 << "个职工姓名:";
			std::cin >> name;
			//岗位选择
			int state = 0;
			std::cout << "请选择该职工的岗位:" << std::endl;
			std::cout << "1、普通职工" << std::endl;
			std::cout << "2、经理" << std::endl;
			std::cout << "3、老板" << std::endl;
			do {
				state = 0;//默认执行一次
				std::cout << "选择该职工的岗位:" << std::endl;
				std::cin >> dId;
				if (dId != 1 && dId != 2 && dId != 3) {//不合法重复执行
					state = 1;
				}
			} while (state);
			//信息录入
			Worker* worker = NULL;
			switch (dId) {//根据职位调用不同函数
			case 1://普通员工
				worker = new Employee(id, name, 1);
				break;
			case 2://经理
				worker = new Manager(id, name, 2);
				break;
			case 3://老板
				worker = new Boss(id, name, 3);
				break;
			default://意外不保存
				break;
			}
			//存入新空间
			int t = this->empNum + i;
			if (t <newSize) {//不判断同上警报报错
				newSpace[t] = worker;
			}
		}
		//释放原有空间
		delete[] this->empArray;	//释放数组空间
		//更改新空间指向
		this->empArray = newSpace;
		//更新个数
		this->empNum = newSize;
		//提示信息
		std::cout << "\n成功添加" << addNum << " 名新职工!" << std::endl;
	}
	else {//输入数据不合法
		std::cout << "输入数据不合法" << std::endl;
	}
	system("pause");
	system("cls");
}

WorkerManager.cpp的析构函数中,释放堆区数据

WorkerManager::~WorkerManager()
{
	if (this->m_EmpArray != NULL)
	{
		delete[] this->m_EmpArray;
	}
}

7.3 测试添加

在main函数分支 1 选项中,调用添加职工接口

至此,添加职工到程序中功能实现完毕

8、文件交互 - 写文件

功能描述:对文件进行读写

​ 在上一个添加功能中,我们只是将所有的数据添加到了内存中,一旦程序结束就无法保存了

​ 因此文件管理类中需要一个与文件进行交互的功能,对于文件进行读写操作

8.1 设定文件路径

首先我们将文件路径,在workerManager.h中添加宏常量,并且包含头文件 fstream

#include <fstream>
#define  FILENAME "empFile.txt"

8.2 成员函数声明

workerManager.h中类里添加成员函数 void save()

//保存文件
void save();

8.3 保存文件功能实现

void WorkerManager::save()
{
	ofstream ofs;
	ofs.open(FILENAME, ios::out);


	for (int i = 0; i < this->m_EmpNum; i++)
	{
		ofs << this->m_EmpArray[i]->m_Id << " " 
			<< this->m_EmpArray[i]->m_Name << " " 
			<< this->m_EmpArray[i]->m_DeptId << endl;
	}

	ofs.close();
}

8.4 保存文件功能测试

在添加职工功能中添加成功后添加保存文件函数
再次运行代码,添加职工
同级目录下多出文件,并且保存了添加的信息

9、文件交互 - 读文件

功能描述:将文件中的内容读取到程序中

虽然我们实现了添加职工后保存到文件的操作,但是每次开始运行程序,并没有将文件中数据读取到程序中

而我们的程序功能中还有清空文件的需求

因此构造函数初始化数据的情况分为三种

  1. 第一次使用,文件未创建
  2. 文件存在,但是数据被用户清空
  3. 文件存在,并且保存职工的所有数据

9.1 文件未创建

workerManager.h中添加新的成员属性 m_FileIsEmpty标志文件是否为空

	//标志文件是否为空
	bool m_FileIsEmpty;

修改WorkerManager.cpp中构造函数代码

//职工类构造函数
WorkerManager::WorkerManager() {
	std::ifstream ifs;//文件读取流对象
	ifs.open(FILENAME, std::ios::in);

	//文件不存在
	if (!ifs.is_open()) {
		//std::cout << "文件不存在" << std::endl;//测试输出
		this->empNum = 0;//初始化人数
		this->fileIsEmpty = true;//初始化文件为空标志
		this->empArray = NULL;//初始化数组指针
		ifs.close();//关闭文件
		return;
	}
}

删除文件后,测试文件不存在时初始化数据功能

9.2 文件存在且数据为空

workerManager.cpp中的构造函数追加代码:

	//文件存在-没有记录
	char ch;
	ifs >> ch;//读取一个字符--如果为空读取的时文件结束判断位
	if (ifs.eof()) {//到达文件尾
		this->empNum = 0;//初始化人数
		this->fileIsEmpty = true;//初始化文件为空标志
		this->empArray = NULL;//初始化数组指针
		ifs.close();//关闭文件
		return;
	}

将文件创建后清空文件内容,并测试该情况下初始化功能

我们发现文件不存在或者为空清空 m_FileIsEmpty 判断文件是否为空的标志都为真,那何时为假?

成功添加职工后,应该更改文件不为空的标志

void WorkerManager::Add_Emp() 成员函数中添加:

		//更新职工不为空标志
		this->fileIsEmpty = false;

9.3 文件存在且保存职工数据

9.3.1 获取记录的职工人数

workerManager.h中添加成员函数 int get_EmpNum();

	//统计人数
	int get_EmpNum();

workerManager.cpp中实现

//统计文件中的人数
int WorkerManager::getNum() {//通过读取文件获取文件数目
	std::ifstream ifs;
	ifs.open(FILENAME, std::ios::in);//读取
	//中间变量
	int id;
	std::string name;
	int dId;

	int num = 0;//统计数据
	while (ifs >> id && ifs >> name && ifs >> dId) {//每次从文件中读取三个数据(一组为一个人的)
		//记录人数
		num++;
	}
	ifs.close();//关闭文件
	return num;//返回数据
}

workerManager.cpp构造函数中继续追加代码:

	//文件存在有数据
	int num = this->getNum();
	std::cout << "职工个数为:" << num << std::endl;
	this->empNum = num;//更新成员属性

手动添加一些职工数据,测试获取职工数量函数

9.3.2 初始化数组

根据职工的数据以及职工数据,初始化workerManager中的Worker ** m_EmpArray 指针

WorkerManager.h中添加成员函数 void init_Emp();

	//初始化文件中员工
	void initEmp();

WorkerManager.cpp中实现

//初始化文件中的员工
void WorkerManager::initEmp() {//从文件中读取对象数据并存储到数组中
	std::ifstream ifs;
	ifs.open(FILENAME, std::ios::in);//读取文件
	int id;
	std::string name;
	int dId;
	int index = 0;
	while (ifs >> id && ifs >> name && ifs >> dId) {
		Worker* worker = NULL;
		//根据不同职位创建不同的对象
		if (dId == 1) {//1 普通员工
			worker = new Employee(id, name, dId);
		}
		else if (dId == 2) {//2 经理
			worker = new Manager(id, name, dId);
		}
		else if (dId == 3) {//3 老板
			worker = new Boss(id, name, dId);
		}
		//存放在数组中
		this->empArray[index] = worker;
		index++;
	}
}

workerManager.cpp构造函数中追加代码

	//根据职工数创建数组
	this->empArray = new Worker * [this->empNum];
	//初始化职工到数组
	initEmp();
	//测试初始化
	/*for (int i = 0; i < empNum; i++) {
		std::cout << "职工号:" << this->empArray[i]->id
			<< "\t职工姓名:" << this->empArray[i]->name
			<< "\t部门编号:" << this->empArray[i]->deptId << std::endl;
	}*/

运行程序,测试从文件中获取的数据
至此初始化数据功能完毕,测试代码可以注释或删除掉!

10、显示职工

功能描述:显示当前所有职工信息

10.1 显示职工函数声明

workerManager.h添加成员函数 void Show_Emp();

	//显示职工
	void Show_Emp();
10.2 显示职工函数实现

workerManager.cpp中实现成员函数 void Show_Emp();

//显示职工
void WorkerManager::showEmp() {
	//判断数据存不存在
	if (this->fileIsEmpty) {
		std::cout << "文件不存在或者为空" << std::endl;
	}
	else {
		for (int i = 0; i < empNum; i++) {
			//利用多态调用接口
			this->empArray[i]->showInfo();
		}
	}
	//暂停屏幕
	system("pause");
	system("cls");
}
10.3 测试显示职工

在main函数分支 2 选项中,调用显示职工接口

测试时分别测试 文件为空和文件不为空两种情况

测试1-文件不存在或者为空情况

测试2 - 文件存在且有记录情况

1546496947671

测试完毕,至此,显示所有职工信息功能实现

11、删除职工

功能描述:按照职工的编号进行删除职工操作

11.1 删除职工函数声明

workerManager.h中添加成员函数 void Del_Emp();

	//删除职工
	void delEmp();
11.2 职工是否存在函数声明

很多功能都需要用到根据职工是否存在来进行操作如:删除职工、修改职工、查找职工

因此添加该公告函数,以便后续调用

workerManager.h中添加成员函数 int IsExist(int id);

	//按照职工编号判断职工是否存在,若存在返回职工在数组中位置,不存在返回-1
	int isExit(int id);
11.3 职工是否存在函数实现

workerManager.cpp中实现成员函数 int IsExist(int id);

//按照职工编号判断职工是否存在,若存在返回职工在数组中位置,不存在返回-1
int WorkerManager::isExit(int id) {
	int index = -1;
	for (int i = 0; i < this->empNum; i++) {
		if (this->empArray[i]->id == id) {//职工号存在
			index = i;
			break;
		}
	}
	return index;
}
11.4 删除职工函数实现

workerManager.cpp中实现成员函数 void Del_Emp();

//删除职工
void WorkerManager::delEmp() {
	//1 文件不存在或者无数据
	if (this->fileIsEmpty) {
		std::cout << "文件不存在或者记录为空" << std::endl;
	}
	else {
		//按照职工编号删除
		std::cout << "请输入想要删除的职工号:";
		int id = 0;
		std::cin >> id;
		int index = this->isExit(id);
		if (index != -1) {//数据存在
			for (int i = index; i < this->empNum; i++) {//从待删除数据往后数据前移
				this->empArray[i] = this->empArray[i + 1];
			}
			this->empNum--;
			this->save();//删除后数据同步到文件
			std::cout << "删除成功" << std::endl;
		}
		else {//数据不存在
			std::cout << "删除失败,未找到该职工" << std::endl;
		}
	}
	system("pause");
	system("cls");
}
11.5 测试删除职工

在main函数分支 3 选项中,调用删除职工接口

测试1 - 删除不存在职工情况
测试2 - 删除存在的职工情况
再次显示所有职工信息,确保已经删除

1546500361889

查看文件中信息,再次核实员工已被完全删除
至此,删除职工功能实现完毕!

12、修改职工

功能描述:能够按照职工的编号对职工信息进行修改并保存

12.1 修改职工函数声明

workerManager.h中添加成员函数 void Mod_Emp();

	//修改职工
	void modEmp();
12.2 修改职工函数实现

workerManager.cpp中实现成员函数 void Mod_Emp();

//修改职工
void WorkerManager::modEmp() {
	if (this->fileIsEmpty) {//文件不存在或者为空
		std::cout << "文件不存在或者记录为空" << std::endl;
	}
	else {
		std::cout << "请输入修改职工的编号:";
		int id;
		std::cin >> id;

		int index = this->isExit(id);
		if (index != -1) {//职工号存在
			//获取原有数据
			int id = this->empArray[index]->id;
			std::string name = this->empArray[index]->name;
			int dId = this->empArray[index]->deptId;
			//修改数据
			//姓名
			std::cout << "原有姓名:" <<name<< "修改为姓名:";
			std::cin >> name;
			//岗位选择
			int state = 0;
			std::cout << "原有岗位:"<<dId<<"请选择该职工的岗位:" << std::endl;
			std::cout << "1、普通职工" << std::endl;
			std::cout << "2、经理" << std::endl;
			std::cout << "3、老板" << std::endl;
			do {
				state = 0;//默认执行一次
				std::cout << "选择该职工的岗位:";
				std::cin >> dId;
				if (dId != 1 && dId != 2 && dId != 3) {//不合法重复执行
					state = 1;
				}
			} while (state);
			//信息录入
			Worker* worker = NULL;
			switch (dId) {//根据职位调用不同函数
			case 1://普通员工
				worker = new Employee(id, name, 1);
				break;
			case 2://经理
				worker = new Manager(id, name, 2);
				break;
			case 3://老板
				worker = new Boss(id, name, 3);
				break;
			default://意外不保存
				break;
			}
			//删除原有数据
			delete this->empArray[index];
			//更新数据,数据保存
			this->empArray[index] = worker;
			//修改完成提示
			std::cout << "修改完成" << std::endl;
			//保存到文件中
			this->save();
		}
		else {
			std::cout << "修改失败,查无此人" << std::endl;
		}
	}
	//按任意按键 清屏
	system("pause");
	system("cls");
}
12.3 测试修改职工

在main函数分支 4 选项中,调用修改职工接口

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-MVB7wraX-1675440464800)(null)]

测试1 - 修改不存在职工情况

测试2 - 修改存在职工情况,例如将职工 “李四” 改为 “赵四”

1546502830350

修改后再次查看所有职工信息,并确认修改成功
再次确认文件中信息也同步更新
至此,修改职工功能已实现!

13、查找职工

功能描述:提供两种查找职工方式,一种按照职工编号,一种按照职工姓名

13.1 查找职工函数声明

workerManager.h中添加成员函数 void Find_Emp();

	//查找职工
	void findEmp();
13.2 查找职工函数实现

workerManager.cpp中实现成员函数 void Find_Emp();

//查找职工
void WorkerManager::findEmp() {
	//文件不存在或者数据为空
	if (this->fileIsEmpty) {
		std::cout << "文件不存在或者数据为空" << std::endl;
	}
	else {
		std::cout << "请选择查找方式:" << std::endl
			<< "1 按照职工编号查找" << std::endl
			<< "2 按照职工姓名查找" << std::endl;
		int select = 0;
		do {//查找选择
			std::cout << "查找方式:";
			std::cin >> select;
		} while (select != 1 && select != 2);
		if (select == 1) {// 按照职工编号查找
			int id;
			std::cout << "请输入职工编号:";
			std::cin >> id;
			int index = isExit(id);//判断数据是否存在
			if (index != -1) {
				std::cout << "查找成功,职工信息如下:" << std::endl;
				this->empArray[index]->showInfo();
			}
			else {
				std::cout << "查找失败,查无此人" << std::endl;
			}
		}
		else if (select == 2) {//按照姓名查找
			std::string name;
			std::cout << "请输入查找的姓名:";
			std::cin >> name;
			//比对信息
			bool flag = false;//查找标志
			for (int i = 0; i < empNum; i++) {
				if (this->empArray[i]->name == name) {
					std::cout << "查找成功!姓名为" << name 
						<< "的信息如下:"<<std::endl;
					flag = true;
					this->empArray[i]->showInfo();
				}
			}
			if (flag == false) {//查找失败
				std::cout << "查询失败,查无此人" << std::endl;
			}
		}
		else {
			std::cout << "输入选项错误" << std::endl;
		}
	}
	system("pause");
	system("cls");
}
13.3 测试查找职工

在main函数分支 5 选项中,调用查找职工接口

测试1 - 按照职工编号查找 - 查找不存在职工

测试2 - 按照职工编号查找 - 查找存在职工

测试3 - 按照职工姓名查找 - 查找不存在职工

测试4 - 按照职工姓名查找 - 查找存在职工(如果出现重名,也一并显示,在文件中可以添加重名职工)

例如 添加两个王五的职工,然后按照姓名查找王五

至此,查找职工功能实现完毕!

14、排序

功能描述:按照职工编号进行排序,排序的顺序由用户指定

14.1 排序函数声明

workerManager.h中添加成员函数 void Sort_Emp();

	//排序职工
	void sortEmp();
14.2 排序函数实现

workerManager.cpp中实现成员函数 void Sort_Emp();

//排序职工信息
void WorkerManager::sortEmp() {
	//文件不存在或者数据为空
	if (this->fileIsEmpty) {
		std::cout << "文件不存在或者信息为空" << std::endl;
	}
	else {
		std::cout<< "请选择排序方式:" << std::endl
			<< "1 按职工号升序排序" << std::endl
			<< "2 安置工号降序排列" << std::endl;
		int select = 0;
		do {
			std::cout << "选择排序:";
			std::cin >> select;
		} while (select != 1 && select != 2);
		//选择排序
		for (int i = 0; i < empNum; i++) {
			int Max = i;
			for (int j = i + 1; j < empNum; j++) {
				//升序排列
				if (select == 1) {
					if (empArray[Max]->id > empArray[j]->id) {
						Max = j;
					}
				}
				else {//降序排序
					if (empArray[Max]->id < empArray[j]->id) {
						Max = j;
					}
				}
			}
			if (i != Max) {//数据交换--每次大循环的最大/小值
				Worker* temp = empArray[i];
				empArray[i] = empArray[Max];
				empArray[Max] = temp;
			}
		}
		std::cout << "排序成功,排序后的结果为:" << std::endl;
		this->save();//保存到文件
		this->showEmp();
	}
}
14.3 测试排序功能

在main函数分支 6 选项中,调用排序职工接口

测试:

首先我们添加一些职工,序号是无序的
测试 - 升序排序 文件同步更新

测试 - 降序排序 文件同步更新
至此,职工按照编号排序的功能实现完毕!

15、清空文件

功能描述:将文件中记录数据清空

15.1 清空函数声明

workerManager.h中添加成员函数 void Clean_File();

	//清空文件
	void clearFile();
15.2 清空函数实现

workerManager.cpp中实现员函数 void Clean_File();

//清空文件
void WorkerManager::clearFile() {
	//确认提示
	int select = 0;
	do {
		std::cout << "你确认要清空?" << std::endl
			<< "1 确认" << std::endl
			<< "2 返回" << std::endl
			<< "选择:";
		std::cin >> select;
	} while (select != 1 && select != 2);
	//清空文件
	if (select == 1) {
		//文件清空
		std::ofstream ofs(FILENAME, std::ios::trunc);//如果文件存在,先删除再建立
		ofs.close();
		//清空堆区对象
		if (this->empArray != NULL) {
			//删除堆区的每个职工对象
			for (int i = 0; i < empNum; i++) {
				if (this->empArray[i] != NULL) {
					delete this->empArray[i];//释放每个堆区对象
				}
			}
			//删除堆区数组指针

			delete[] this->empArray;
			this->empArray = NULL;
			this->empNum = 0;
			this->fileIsEmpty = true;
		}
		std::cout << "清除成功!" << std::endl;
	}
	system("pause");
	system("cls");
}
15.3 测试清空文件

在main函数分支 7 选项中,调用清空文件接口

测试:确认清空文件
再次查看文件中数据,记录已为空
打开文件,里面数据已确保清空,该功能需要慎用!

随着清空文件功能实现,本案例制作完毕 ^ _ ^

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值