C++核心 基于多态的职工管理系统
基于多态的增删改查
worker.h 这是一个抽象基类,作为借口让其余三个子类接入
class worker
{
public:
virtual void show_info()=0;
virtual string get_bumen()=0;
int id;
string name;
int bumen;
};下面是BOSS.H和BOSS.CPP,员工和经理的cpp,h都类似,这里就是worker虚函数实现的地方。
这样便可以使用多态接入。 我们在定义一个新员工时,不知道他是这三种中的哪种便可以使用worker。
#pragma once
#include "iostream"
#include "string"
#include "worker.h"
using namespace std;
class BOSS:public worker
{
public:
BOSS(int newid, string newname, int newbumen);
void show_info();
string get_bumen();
};#include "BOSS.h"
void BOSS::show_info()
{
cout<<"职工编号 "<< this->id
<< " \t职工姓名: " << this->name
<< " \t岗位:" << this->get_bumen()
<< " \t岗位职责:完成公司所有事务" << endl;
}
string BOSS::get_bumen()
{
return string("大老板");
}
//构造函数
BOSS::BOSS(int newid, std::string newname, int newbumen)
{
this->id=newid;
this->name=newname;
this->bumen=newbumen;
}这是管理系统的.h
#pragma once
#include "iostream"
#include "string"
#include "worker.h"
#include "jingli.h"
#include "yuangong.h"
#include "BOSS.h"
#include "fstream"
using namespace std;
#define FILENAME "book.txt"
class Management_system
{
public:
//构造函数
Management_system();
//析构函数
~Management_system();
//菜单展示
void show_menu();
//退出功能
void exit_system();
//添加职工
void addworker();
//保存当前职工管理系统中所有人的信息进文件
void save();
//得到目前职工人数
int get_num();
//文件里有人 就初始化数组把文件里的人搞到数组里来
void init();
//显示职工
void show_all();
//删除职工
void cleanone();
//找到某个职工
int findone(int id);
//修改职工
void modify();
//查找职工
void showone();
//排序职工
void SORT();
//清空函数
void cleanall();
bool isempty;
int max_num;
worker** arry;
};
添加职工功能
如果本来就有职工,那就把原来所有职工中的数据都迁移到现在这个新数组中来。所以需要扩展数组空间
使用了一个worker**[]数组来存放信息,是存放指针的数组
void Management_system::addworker()
{
cout<<"请输入添加职工的数量:"<<endl;
int addnum=0;
cin>>addnum;
if(addnum>0)
{
int newsize=addnum+this->max_num;
//这里定义一个存放worker*指针的数组,
worker**newspace=new worker * [newsize];
//把原有数组中的工作人员复制到新数组中
if(this->arry!=NULL)
{
for(int i=0;i<this->max_num;i++)
{
newspace[i]=this->arry[i];
}
}
//接受新输入的工作人员
for(int i=0;i<addnum;i++)
{
int newid;string newname;int newbumen;
cout << "请输入第 " << i + 1 << " 个新职工编号:" << endl;
cin >> newid;
cout << "请输入第 " << i + 1 << " 个新职工姓名:" << endl;
cin >> newname;
cout << "请选择该职工的岗位:" << endl;
cout << "1、普通职工" << endl;
cout << "2、经理" << endl;
cout << "3、老板" << endl;
cin>>newbumen;
worker*newworker=NULL;
switch (newbumen)
{
case 1: newworker=new yuangong(newid,newname,1);break;
case 2: newworker=new jingli(newid,newname,2);break;
case 3: newworker=new BOSS(newid,newname,3);break;
default: break;
}
newspace[i+this->max_num]=newworker;
}
//更新管理系统
delete[] this->arry; // 释放指针数组
this->arry=newspace;this->max_num=newsize;
cout<<"成功添加第"<<addnum<<"位新员工"<<endl;
this->save();
this->isempty=0;
}else
{
cout<<"输入有误"<<endl;
}
system("pause");
system("cls");
}退出功能
void Management_system::exit_system()
{
cout<<"欢迎下次使用"<<endl;
system("pause");
exit(0);
}
写文件
当前数组中的所有元素写入文件中存储
void Management_system::save()
{
ofstream ofs;
ofs.open(FILENAME,ios::out);
if(this->arry!=NULL)
{
for(int i=0;i<this->max_num;i++)
{
ofs<<this->arry[i]->id<<" "
<<this->arry[i]->name<<" "
<<this->arry[i]->bumen<<endl;
}
}
ofs.close();
}初始化数组
如果文件中本来就有内容,我们需要把他读入进数组方便操作
void Management_system::init()
{
ifstream ifs;
ifs.open(FILENAME,ios::in);
int id;string name;int bumen;
int index=0;
while(ifs>>id&&ifs>>name&&ifs>>bumen)
{
worker*nw=NULL;
switch (bumen)
{
case 1: nw=new yuangong(id,name,1);break;
case 2: nw=new jingli(id,name,2);break;
case 3: nw=new BOSS(id,name,3);break;
default: break;
}
this->arry[index++]=nw;
}
}
获取文件中的人数
int Management_system::get_num()
{
ifstream ifs;
ifs.open(FILENAME,ios::in);
int ans=0;
int id;string name;int bumen;
while(ifs>>id&&ifs>>name&&ifs>>bumen)
{ans++;}
ifs.close();
return ans;
}构造函数
分三种情况,如果文件没有创建, 有文件但是记录为空,文件有记录,那就init把他传入数组
这里有个char ch,ifs>>ch; 意思是定义一个字符,用字符去读取ifs文件中的第一个字符,他会自动跳过空格或者各种控制符
ifs.eof(),意思是判断ifs是不是读到了文件末尾; 如果读一个字符就读到了文件尾那就是空,返回true
Management_system::Management_system()
{
ifstream ifs;
ifs.open(FILENAME,ios::in);
//文件如果未创建
if(!ifs.is_open()) //检查文件是否成功打开
{
cout<<"文件不存在"<<endl;
this->max_num=0;
this->isempty=1;
this->arry=NULL;
ifs.close();
return ;
}
//文件存在但是为空
char ch;
ifs>>ch; //这里是读入一个字符
if(ifs.eof())
{
cout<<"文件为空"<<endl;
this->max_num=0;
this->isempty=1;
this->arry=NULL;
ifs.close();
return ;
}
//文件存在也有数据
int num=this->get_num();
cout<<"职工个数为"<<num<<endl;
this->max_num=num;
this->arry=new worker*[num];
init();
// for(int i=0;i<this->max_num;i++)
// {
// this->arry[i]->show_info();
// }
}显示职工
void Management_system::show_all()
{
if(this->arry==NULL)cout<<"文件不存在或记录为空"<<endl;
else
{
for(int i=0;i<this->max_num;i++)
{
this->arry[i]->show_info();
}
}
system("pause");
system("cls");
}找到某个职工
int Management_system::findone(int id)
{
int ans=-1;
for(int i=0;i<this->max_num;i++)
{
if(this->arry[i]->id==id)
{ans=i;break;}
}
return ans;
}删除职工
void Management_system::cleanone()
{
if(this->arry==NULL)
{
cout<<"文件不存在或记录为空"<<endl;
}
else
{
cout << "请输入想要删除的职工号:" << endl;
int id;cin>>id;
int index=this->findone(id);
if(index!=-1)
{
for(int i=index;i<this->max_num;i++)
{
this->arry[i]=this->arry[i+1];
}
this->max_num--;
cout << "删除成功!" << endl;
this->save();
}
else
{
cout << "删除失败,未找到该职工" << endl;
}
}
}修改职工
void Management_system::modify()
{
if(this->arry==NULL)
{
cout<<"文件不存在或记录为空"<<endl;
}else
{
cout << "请输入修改职工的编号:" << endl;
int id;
cin >> id;
int index= findone(id);
if(index!=-1)
{
delete this->arry[index];
int newid;string newname;int newbumen;
cout << "查到: " << id << "号职工,请输入新职工号: " << endl;
cin >> newid;
cout << "请输入新姓名: " << endl;
cin >> newname;
cout << "请输入岗位: " << endl;
cout << "1、普通职工" << endl;
cout << "2、经理" << endl;
cout << "3、老板" << endl;
cin>>newbumen;
worker*newworker=NULL;
switch (newbumen)
{
case 1: newworker=new yuangong(newid,newname,1);break;
case 2: newworker=new jingli(newid,newname,2);break;
case 3: newworker=new BOSS(newid,newname,3);break;
default: break;
}
this->arry[index]=newworker;
cout << "修改成功!" << endl;
this->save();
}else
{
cout << "修改失败,查无此人" << endl;
}
}
system("pause");
system("cls");
}查找职工
void Management_system::showone()
{
if(this->arry==NULL)
{
cout<<"文件不存在或记录为空"<<endl;
}else
{
cout << "请输入查找的方式:" << endl;
cout << "1、按职工编号查找" << endl;
cout << "2、按姓名查找" << endl;
int sel=0;
cin>>sel;
if(sel==1)
{
int id;
cout << "请输入查找的职工编号:" << endl;
cin >> id;
int index;
index= findone(id);
if(index!=-1)
{
cout << "查找成功!该职工信息如下:" << endl;
this->arry[index]->show_info();
}else
{
cout << "查找失败,查无此人" << endl;
}
}else if(sel==2)
{
string name;
cout << "请输入查找的姓名:" << endl;
cin >> name;
bool flag=0;
for(int i=0;i<this->max_num;i++)
{
if(name==this->arry[i]->name)
{
flag==1;
cout << "查找成功!该职工信息如下:" << endl;
this->arry[i]->show_info();
break;
}
}
if(flag==0)
{
cout << "查找失败,查无此人" << endl;
}
}else
{
cout << "输入选项有误" << endl;
}
}
system("pause");
system("cls");
}排序职工
这里使用了选择排序
void Management_system::SORT()
{
if(this->arry==NULL)
{
cout<<"文件不存在或记录为空"<<endl;
}else
{
cout << "请选择排序方式: " << endl;
cout << "1、按职工号进行升序" << endl;
cout << "2、按职工号进行降序" << endl;
int sel=0;
cin>>sel;
for(int i=0;i<this->max_num;i++)
{
int minormax=i;
for(int j=i+1;j<this->max_num;j++)
{
if(sel==1)
{
if(this->arry[minormax]->id>this->arry[j]->id)
{
minormax=j;
}
}else
{
if(this->arry[minormax]->id<this->arry[j]->id)
{
minormax=j;
}
}
if(i!=minormax)
{
worker * temp = this->arry[i];
this->arry[i]=this->arry[minormax];
this->arry[minormax]=temp;
}
}
}
cout << "排序成功,排序后结果为:" << endl;
this->save();
this->show_all();
}
}清空职工
trunc 是什么?
trunc 是 C++ 文件流(ofstream)的打开模式,完整写法是 ios::trunc,表示截断(truncate)文件,即清空已有内容,然后重新写入数据。
ios::trunc 作用
当你以 ios::out | ios::trunc 模式打开文件时:
如果文件已存在,它的内容会被清空。
如果文件不存在,则创建一个新文件。
void Management_system::cleanall()
{
cout << "确认清空?" << endl;
cout << "1、确认" << endl;
cout << "2、返回" << endl;
int sel;
cin>>sel;
if(sel==1)
{
ofstream ofs;
ofs.open(FILENAME,ios::trunc);
ofs.close();
if(this->arry!=NULL)
{
for(int i=0;i<this->max_num;i++)
{
if(this->arry[i]!=NULL)
{
delete this->arry[i];
}
}
delete[] this->arry;
this->max_num=0;
this->arry=NULL;
this->isempty=1;
}
cout << "清空成功!" << endl;
}
system("pause");
system("cls");
}析构函数和展示菜单
//析构函数
Management_system::~Management_system()
{
if (this->arry != NULL)
{
for (int i = 0; i < this->max_num; i++) {
delete this->arry[i]; // 释放每个 worker 对象
}
delete[] this->arry; // 释放指针数组
}
}
//展示菜单
void Management_system::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;
cout << endl;
}问题1,woker定义好之后,在员工,经理,老板的类里又重定义了各种信息,导致数据存储的时候发生错误
问题2,没有ofs.close()