职工管理系统C++实现

在数据结构学习到图时,我停下了继续学习数据结构的脚步,回过头来复习了下C++的语法,通过一个职工管理系统完成了复习,这个小项目有很多值得我去学习的地方,改天我给他打印出来充分吸收,今天先上代码,明天再补上思考和一些坑。

#include<iostream>
#include"workerManger.h"
#include"Boss.h"
#include"Worker.h"
#include"Jingli.h"
#include"Pugong.h"
#include<string>
using namespace std;
int main()
{
	workerManger a;
	//cout<<a.Getlength()<<endl;
	int choice = 0;
	//测试代码
	//Worker* p1 = new Jingli(1, "张三", 3);
	
	/*Worker* p2 = new Pugong(1, "张三", 3);
	Worker* p3 = new Boss(1, "张三", 3);
	p1->showInfo();
	p2->showInfo();
	p3->showInfo();*/
	while (true)
	{
		a.Show_menu();
		cin >> choice;
		switch (choice)
		{
		case 0:a.Exitsystem(); break;                    //退出循环
		case 1:a.Addemptor(); break;                     //增加
		case 2:a.Print(); break;                         //显示
		case 3:a.Delete(); break;                        //删除
		case 4:a.Change(); break;                        //修改
		case 5:a.Search(); break;                        //查找
		case 6:a.sort(); break;                          //排序
		case 7:a.Clearfile(); break;                     //清空
		default:system("cls"); break;
		}
	}
	system("pause");
	return 0;
}
#pragma once//防止重复包含
#include<iostream>
#include<string>
#include"Worker.h"
#include<fstream>
#define FILENAME "empfile.txt"
using namespace std;
class workerManger
{
public:
	workerManger();
	~workerManger();
	//展示菜单
	void Show_menu();
	void Exitsystem();
	//人数
	int m_Empnum;
	//职工数组的指针,开辟于堆区的数组(各父指针的数组)
	Worker** m_EmpArray;
	bool m_Fileempty;                                 //从文件中读取数据,用来判断是否为空文件
	void Addemptor();                                 //插入数的职工
	void Addsingle();                                 //插入单个职工,这里采用父指针指向各个不同的子对象,对父指针进行存储
	void save();                                      //保存函数
	void Print();                                     //显示函数
	void Delete();                                    //删除函数
	void Numdelete();                                 //序号删
	void Namedelete();                                //姓名删
	void Search();                                    //查号函数
	void Namesearch();                                //姓名查
	void Numsearch();                                 //序号查
	void Change();                                    //修改
	void sort();                                      //排序
	void Highsort();                                  //由高到低排
	void Lowsort();                                   //由低到高排
	void Clearfile();                                 //清楚文件
};


#include "workerManger.h"
#include"Boss.h"
#include"Jingli.h"
#include"Worker.h"
#include"Pugong.h"
#include<string>
workerManger::workerManger()
{
	初始化,限免这种初始化会造成文件对象创建时没有任何数据
	//这是不对的,应为我们要从文件中读取数据过来,所以重写初始化函数
	//使兑现能够从文件中读取到数据。
	//有这三种情况,一没有此类文件,二,由此文件但为空,三由此文件且有数据
	/*this->m_Empnum = 0;
	this->m_EmpArray = NULL;
	this->m_Fileempty = true;*/
	ifstream ifs;
	ifs.open(FILENAME, ios::in);
	//1.文件不存在
	if (!ifs.is_open())
	{
		this->m_Empnum = 0;
		this->m_EmpArray = NULL;
		this->m_Fileempty = true;
		ifs.close();
		cout << "文件不存在" << endl;
		ifs.close();
		return;
	}
	//2.文件存在,但为空
	char ch;
	ifs >> ch;
	if (ifs.eof())
	{

		this->m_Empnum = 0;
		this->m_EmpArray = NULL;
		this->m_Fileempty = true;
		cout << "文件为空" << endl;
		ifs.close();
		return;
	}
	//这里加一个文件指针重定位头比较好,但是我不会,所以,笨方法,先关闭文件,再打开文件,以确保文件指针移到头部,防止下面的变量读不上去。
	ifs.close();
	//3.文件存在,且有数据,把文件加载到程序中
	//由于是采用数组对数据进行存储,所以需要事先知道里面有几个数据
	ifs.open(FILENAME, ios::in);
	int sum=0;//用于存储人数
	string name;//用于存储名字
	int id;//用于存储id;
	int did;//用于存储did
	while (ifs >> id && ifs >> name && ifs >> did)
	{
		sum++;
	}//获取到所有数据数量的员工
	cout << "文件中当前含有" <<sum<<"个员工"<< endl;
	this->m_Empnum = sum;
	ifs.close();//关闭文件
	ifs.open(FILENAME, ios::in);//重新打开文件
	this->m_EmpArray = new Worker * [sum];//申请出这么大空间
	Worker* p=NULL;//申请出一个员工指针
	for (int i = 0; i < sum; i++)
	{
		ifs >> id;
		ifs >> name;
		ifs >> did;
		switch (did)
		{
		case 1:p = new Pugong(id, name, did); break;
		case 2:p = new Jingli(id, name, did); break;
		case 3:p = new Boss(id, name, did); break;
		}
		this->m_EmpArray[i] = p;
	}
	ifs.close();

}
//int workerManger::Getlength()
//{
//
//	int sum=0;
//	ifstream ifs;
//	ifs.open(FILENAME, ios::in);
//	int id;
//	string name;
//	int did;
//	while (ifs >> id && ifs >> name && ifs >> did)
//	{
//		sum++;
//	}
//	ifs.close();
//	return sum;
//}

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

}
void workerManger::Exitsystem()
{
	cout << "欢迎下次使用!" << endl;
	system("pause"); 
	exit(0);
}
void workerManger::Addsingle()//尾插单个指针
{
	system("cls");
	this->m_Empnum = this->m_Empnum + 1;              //首先人数+1
	Worker** newArray = new Worker* [this->m_Empnum];  //申请大空间
	
	for (int i = 0; i < this->m_Empnum-1; i++)        //将原本数据复制到大空间中
	{
		newArray[i] = this->m_EmpArray[i];
	}//将原本的复制过去
	int id;//职工的id
	string name;//职工的姓名
	int did;//职工的部门编号
	cout << "请输入员工的id" << endl;
	cin >> id;
	cout << "请输入员工的姓名" << endl;
	cin >> name;
	cout << "请输入员工的岗位:" << endl;
	cout << "1.普通员工" << endl;
	cout << "2.经理" << endl;
	cout << "3.老板" << endl;
	cin >> did;
	Worker* p = NULL;//根据不同情况创建不同对象,并用父指针指向他们,等会存储父指针即可
	switch (did)
	{
	case 1:p = new Pugong(id, name, did);
		break;
	case 2:p = new Jingli(id, name, did);
		break;
	case 3:p = new Boss(id, name, did);
		break;
	}
	newArray[this->m_Empnum-1] = p;//数组下标从0开始计算,所以所以最后一个存放在下表为数目-1的下表。
	delete[] this->m_EmpArray;
	this->m_EmpArray = newArray;
	this->m_Fileempty = false;//添加成功,职工数量不为0
	this->save();
	system("cls");
}

//写完插入单个节点后,我么来写插入多个节点的函数
void workerManger::Addemptor()
{
	system("cls");
	cout << "请输入你要插入多少人" << endl;
	int sumnum = 0;
	cin >> sumnum;
	if (sumnum > 0)
	{
		for (int i = 0; i < sumnum; i++)
		{
			this->Addsingle();
		}
	}
	else
	{
		cout << "输入有误,退出输入" << endl;
	}

	system("pause");//暂停
	system("cls");//刷新屏幕,清屏
}
workerManger::~workerManger()
{
	delete[] this->m_EmpArray;
	this->m_EmpArray = NULL;
}
void workerManger::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();
}
void workerManger::Print()
{
	system("cls");
	if (this->m_Fileempty==true)
	{
		system("cls");
		cout << "文件为空,禁止访问!" << endl;
		return;//返回主程序
		
	}
	for (int i = 0; i < this->m_Empnum; i++)
	{
		cout << "员工编号: " << this->m_EmpArray[i]->m_Id
			<< "\t员工姓名: " << this->m_EmpArray[i]->m_Name
			<< "\t岗位:" << this->m_EmpArray[i]->Getdeptname()
			<< "\t岗位职责:" << this->m_EmpArray[i]->Getjob()<<endl;
	}
}
void workerManger::Delete()
{
	if (this->m_Fileempty == true)
	{
		system("cls");
		cout << "文件为空,禁止删除" << endl;
		return;//返回主程序
	}
	int choice = 0;
	cout << "请输入你想要的删除的方法:"
		<< "1.按照序号删,2.按照姓名删" << endl;
	cin >> choice;
	switch (choice)
	{
	case 1:this->Numdelete();
		break;
	case 2:this->Namedelete();//姓名删
		break;
	}

}
//序号删
void workerManger::Numdelete()
{
	if (this->m_Fileempty == true)
	{
		cout << "文件为空,禁止访问!" << endl;
		return;//返回主程序
	}
	int num=0;
	cout << "请输入你将要删除的序号:" << endl;
	cin >> num;
	int i = 0;
	while (i<this->m_Empnum)
	{
		if (this->m_EmpArray[i]->m_Id == num)
		{
			break;
		}
		i++;
	}
	if (i >= this->m_Empnum)//说明是循环遍历退出的,所以不存在
	{
		cout << "查无此人" << endl;
		return;
	}
	//此时i移动到下标处
	//所有后面的往前移动
	while (i <= this->m_Empnum - 1)
	{
		this->m_EmpArray[i] = this->m_EmpArray[i + 1];
		i++;
	}
	this->m_Empnum -= 1;
	if (this->m_Empnum == 0)
	{
		this->m_Fileempty = true;
	}
	this->save();
}
//姓名删
void workerManger::Namedelete()
{
	if (this->m_Fileempty == true)
	{
		cout << "文件为空,禁止访问!" << endl;
		return;//返回主程序
	}
	string name;
	cout << "请输入你将要删除的姓名:" << endl;
	cin >> name;
	int i =0;
	while (i < this->m_Empnum)
	{
		if (this->m_EmpArray[i]->m_Name == name)
		{
			break;
		}
		i++;
	}
	if (i >= this->m_Empnum)//说明是循环遍历退出的,所以不存在
	{
		cout << "查无此人" << endl;
		return;
	}
	while (i <= this->m_Empnum - 1)
	{
		this->m_EmpArray[i] = this->m_EmpArray[i + 1];
		i++;
	}
	this->m_Empnum -= 1;
	if (this->m_Empnum == 0)
	{
		this->m_Fileempty = true;
	}
	this->save();
}
void workerManger::Search()
{
	if (this->m_Fileempty == true)
	{
		system("cls");
		cout << "文件为空,禁止查找" << endl;
		return;//返回主程序
	}
	int choice = 0;
	cout << "请输入你想要的查找的方法:"
		<< "1.按照序号找,2.按照姓名找" << endl;
	cin >> choice;
	switch (choice)
	{
	case 1:this->Numsearch();//序号查
		break;
	case 2:this->Namesearch();//姓名查
		break;
	}

}
void workerManger::Namesearch()
{
	if (this->m_Fileempty == true)
	{
		cout << "文件为空,禁止查找" << endl;
		return;//返回主程序
	}
	string name;
	cout << "请输入你将要查找的姓名:" << endl;
	cin >> name;
	int i = 0;
	while (i < this->m_Empnum)
	{
		if (this->m_EmpArray[i]->m_Name == name)
		{
			break;
		}
		i++;
	}
	if (i >= this->m_Empnum)//说明是循环遍历退出的,所以不存在
	{
		cout << "查无此人" << endl;
		return;
	}
	this->m_EmpArray[i]->showInfo();
}
void workerManger::Numsearch()//序号查
{
	if (this->m_Fileempty == true)
	{
		cout << "文件为空,禁止查找" << endl;
		return;//返回主程序
	}
	int num;
	cout << "请输入你将要查找的序号:" << endl;
	cin >> num;
	int i = 0;
	while (i < this->m_Empnum)
	{
		if (this->m_EmpArray[i]->m_Id == num)
		{
			break;
		}
		i++;
	}
	if (i >= this->m_Empnum)//说明是循环遍历退出的,所以不存在
	{
		cout << "查无此人" << endl;
		return;
	}
	this->m_EmpArray[i]->showInfo();
}
//修改要注意啊,此时虽然你通过输入修改了里面的一些参数啊,但是你并没有修改他的类型,所以虽然你修改了里面的东西,但是实际上自对象还是原本的类型,没有改变,所以注意改变其类型,
//即重新申请空间并插入,释放原本的空间。
void workerManger::Change()
{
	if (this->m_Fileempty == true)
	{
		system("cls");
		cout << "文件为空,禁止修改" << endl;
		return;//返回主程序
	}
	int num;
	cout << "请输入你将要修改的序号:" << endl;
	cin >> num;
	int i = 0;
	while (i < this->m_Empnum)
	{
		if (this->m_EmpArray[i]->m_Id == num)
		{
			break;
		}
		i++;
	}//此时i在你要修改的地方
	//注意虽然都是通过父指针只想他们,但是实际上的类型在改变前后不一样,所以要连着子对象的类型一起改
	if (i >= this->m_Empnum)//说明是循环遍历退出的,所以不存在
	{
		cout << "查无此人" << endl;
		return;
	}
	Worker* p = NULL;
	int id;
	string name;
	int did;
	cout << "请输入你要修改的id" << endl;
	cin >> id;
	cout << "请输入你要修改的name" << endl;
	cin >> name;
	cout << "请输入你要修改的did" << endl;
	cin >> did;
	if (did == 1)
	{
		//重新申请子对象空间,应为子对象类型已经改变
		p = new Pugong(id, name, did);
		delete this->m_EmpArray[i];
		this->m_EmpArray[i] = p;
	}
	else if(did==2)
	{
		p = new Jingli(id, name, did);
		delete this->m_EmpArray[i];
		this->m_EmpArray[i] = p;
	}
	else
	{
		p = new Boss(id, name, did);
		delete this->m_EmpArray[i];
		this->m_EmpArray[i] = p;
	}
	this->save();
}
void workerManger::sort()
{
	if (this->m_Fileempty == true)
	{
		system("cls");
		cout << "文件为空,禁止排序" << endl;
		return;//返回主程序
	}
	int choice = 0;
	cout << "请输入将要进行的排序操作1.从高到低。2.从低到高" << endl;
	cin >> choice;
	if (choice == 1)
	{
		this->Highsort();//从高到低排序
		this->save();
	}
	else
	{
		this->Lowsort();//从低到高排
		this->save();
	}
}
void workerManger::Highsort()
{
	//其实此位置不用检查是否为空,由于在排序函数中检查过了,我还要实现具体的函数
	//这个排序交换,不用像上面的修改那样,这里直接交换数组中的父指针即可,子对象随着父指针交换,并没有改变对象的类型

	Worker* temp = NULL;;
	for (int i = 0; i < this->m_Empnum - 1; i++)
	{
		for (int j = 0; j < this->m_Empnum - i-1; j++)
		{
			if ((this->m_EmpArray[j]->m_Id) <( this->m_EmpArray[j + 1]->m_Id))
			{
				temp = this->m_EmpArray[j];
				this->m_EmpArray[j] = this->m_EmpArray[j + 1];
				this->m_EmpArray[j+1] = temp;
			}
		}
	}
}
void workerManger::Lowsort()
{
	Worker* temp;
	for (int i = 0; i < this->m_Empnum - 1; i++)
	{
		for (int j = 0; j < this->m_Empnum - i - 1; j++)
		{
			if (this->m_EmpArray[j]->m_Id > (this->m_EmpArray[j + 1]->m_Id))
			{
				temp = this->m_EmpArray[j];
				this->m_EmpArray[j] = this->m_EmpArray[j + 1];
				this->m_EmpArray[j+1] = temp;
			}
		}
	}
}
void workerManger::Clearfile()
{
	if (this->m_Fileempty == true)
	{
		system("cls");
		cout << "文件为空,禁止清除" << endl;
		return;
	}
	cout << "确定要进行文件删除吗?1.确定。其他.不删了吧!" << endl;
	int choice = 0;
	cin >> choice;
	if (choice == 1)
	{
		//文件删除,先将数组中父指针指向的对象释放,最后释放父指针的数组。
		ofstream ofs;
		ofs.open(FILENAME, ios::trunc);//打开文件并清除文件内容
		ofs.close();
		for (int i = 0; i < this->m_Empnum; i++)
		{
			delete this->m_EmpArray[i];
		}
		delete[] this->m_EmpArray;
		this->m_EmpArray = NULL;
		this->m_Empnum = 0;
		this->m_Fileempty = true;
		
	}
	else 
	{
		cout << "下次请确认后在调用我,别瞎几把调用我,懂???憨批" << endl;
		return;//返回主程序
	}
}

#pragma once
#include<iostream>
using namespace std;
#include<string>
class Worker
{

public:
	virtual void showInfo() = 0;//显示信息
	virtual string Getdeptname() = 0;//获取岗位名称
	virtual string Getjob() = 0;//获取岗位职责
	int m_Id;
	string m_Name;
	int m_Deptid;
};



```cpp
#pragma once
#include<iostream>
#include"Worker.h"
using namespace std;
class Pugong:public Worker
{
public:
	Pugong(int id, string name, int did);
	void showInfo();
	string Getdeptname();
	string Getjob();
};



```cpp
#include "Pugong.h"
Pugong::Pugong(int id, string name, int did)
{
	this->m_Id = id;
	this->m_Name = name;
	this->m_Deptid = did;

}
void Pugong::showInfo()
{
	cout << "员工编号: " << this->m_Id
		<< "\t员工姓名: " << this->m_Name 
		<< "\t岗位:" << this->Getdeptname() 
		<< "\t岗位职责:" << this->Getjob() << endl;
}
string Pugong::Getdeptname()
{
	return "普通员工";
}
string Pugong::Getjob()
{
	return "完成经理布置的任务!";
}
#pragma once
#include"Worker.h"
#include<iostream>
using namespace std;
class Jingli:public Worker
{
public:
	Jingli(int id, string name, int did);
	void showInfo();//显示信息
	string Getdeptname();//获取岗位名称
	string Getjob();//获取岗位职责
};


#include "Jingli.h"
Jingli::Jingli(int id, string name, int did)
{
	this->m_Id = id;
	this->m_Name = name;
	this->m_Deptid = did;
}
void Jingli::showInfo()//显示信息
{
	cout << "员工编号: " << this->m_Id
		<< "\t员工姓名: " << this->m_Name
		<< "\t岗位:" << this->Getdeptname()
		<< "\t岗位职责:" << this->Getjob() <<  endl;
}
string Jingli::Getdeptname()//获取岗位名称
{
	return "经理";
}
string Jingli::Getjob()//获取岗位职责
{
	return "完成老板布置的任务!";
}
#pragma once
#include "Worker.h"
class Boss:public Worker
{
public:
	Boss(int id, string name, int did);
	void showInfo();//显示信息
	string Getdeptname();//获取岗位名称
	string Getjob();//获取岗位职责
};


#include "Boss.h"
Boss::Boss(int id, string name, int did)
{
	this->m_Id = id;
	this->m_Name = name;
	this->m_Deptid = did;
}
void Boss::showInfo()//显示信息
{
	cout << "员工编号: " << this->m_Id
		<< "\t员工姓名: " << this->m_Name
		<< "\t岗位:" << this->Getdeptname()
		<< "\t岗位职责:" << this->Getjob()<< endl;
}
string Boss::Getdeptname()//获取岗位名称
{
	return "老板";
}
string Boss::Getjob()//获取岗位职责
{
	return "管理所有事务!";
}
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值