目录
开始演讲比赛:完成整届比赛的流程,每个比赛阶段需要给用户一个提示,用户按任意键进入下一个比赛阶段
查看往届记录:查看之前比赛前三名结果,每次比赛都会记录到文件中,文件用.csv后缀保存
清空比赛记录:将文件中数据清空
退出比赛程序:可以退出当前程序
1.开始比赛
(1)选择开始比赛
(2)第一轮比赛开始:抽签→打分→晋级名单?
(2)第二轮比赛开始:抽签→比赛打分→晋级选手(最后冠亚季)?
(3)保存第二轮比赛前三名?
2.查看往届记录
3.?清空比赛记录
?4.退出比赛程序:
1.“源文件”? ? ?“右键”? ? “添加”? ? ?“新建项”
2.更改文件名称为“演讲比赛流程管理系统”
在管理类speechManager.h中添加成员函数? void show_Menu();
在main函数中提供分支选择,提供每个功能接口
比赛流程分析:
抽签→开始演讲比赛→显示第一轮比赛结果→
抽签→开始演讲比赛→显示前三名结果→保存比赛分数
speaker.h中创建Speaker类
在speechManager.h头文件中添加成员属性、initSpeech()函数
1.speechManeger.cpp中初始化函数
2.构造函数中调用initSpeech()?
1.speechManager.h中创建speechManager类的creatSpeaker()函数
2.speechManager.cpp中实现creatSpeaker()函数,创建人员、两轮分数均置为0
3. 构造函数中调用creatSpeaker()函数?
4.测试
main()中写入测试代码:
测试结果:
在speechManager.h中提供开始比赛的成员函数void startSpeech(),该函数功能主要控制比赛流程
在speechManager.cpp中实现startSpeech()? ,此处使用了6.3.5的抽签函数
1.声明speechDraw()函数
2.实现speechDraw()函数
3.测试speechDraw()函数
case1的时候调用startSpeech()函数,startSpeech()函数中调用了抽取speechDraw()函数
?测试结果
1.声明speechContest()函数
2.增加头文件
?3.实现speechContest()函数
总结:
void SpeechManager::speechContest()
{
cout << "--------第<<" << this->m_Index << ">>轮比赛正式开始--------" << endl;
//准备临时容器 存放小组成绩
multimap<double, int, greater<double>> groupScore;
int num = 0;// 记录人员个数
vector<int>v_Src;//比赛选手容器
if (m_Index == 1)
{
v_Src = v1;
}
else
{
v_Src = v2;
}
//所有的选手进行比赛
for (vector<int>::iterator it = v_Src.begin(); it != v_Src.end(); it++)
{
num++;
//评委打分
deque<double>d;
for (int i = 0; i < 10; i++)
{
double score = (rand() % 401 + 600) / 10.f; //600~1000
//cout << score << " ";
d.push_back(score);
}
//cout << endl;
sort(d.begin(), d.end(), greater<double>());//排序 从大到小
d.pop_front();//去除最高分
d.pop_back();//去除最低分
double sum = accumulate(d.begin(), d.end(), 0); //分数求和
double avg = sum / (double)d.size(); //平均分
//打印平均分
//cout << "编号: " << *it << " 姓名:" << this->m_Speaker[*it].m_Name << " 平均分" << avg;
//将平均分放入map容器
this->m_Speaker[*it].m_Score[this->m_Index - 1] = avg;
//cout << endl;
//将打分数据放入临时小组容器中
groupScore.insert(make_pair(avg, *it));//key是得分,value是具体选手编号
//六人取出前三名
if (num % 6 == 0)
{
cout << "第 " << num / 6 << " 小组比赛名次:" << endl;
for (multimap<double, int, greater<double>>::iterator it = groupScore.begin(); it != groupScore.end(); it++)
{
cout << "编号: " << it->second << " 姓名:" << this->m_Speaker[it->second].m_Name << " 成绩:"
<< this->m_Speaker[it->second].m_Score[this->m_Index - 1] << endl;
}
//取走前三名
int count = 0;
for (multimap<double, int, greater<double>>::iterator it = groupScore.begin(); it != groupScore.end() && count<3; it++,count++)
{
if (this->m_Index == 1)
{
v2.push_back((*it).second);
}
else
{
vVictory.push_back((*it).second);
}
}
groupScore.clear();//小组容器清空
cout << endl;
}
}
cout<<"--------第<<" << this->m_Index << ">>轮比赛完毕!--------" << endl;
system("pause");
}
?4.测试speechContest()函数?
测试结果:
1.声明showScore()函数
2.实现showScore()函数
3.测试showScore()函数
1.声明saveRecord()函数
?2.实现saveRecord()函数
3.测试saveRecord()函数
测试结果:?
?
1.声明成员函数loadRecord()、是否为空的标志fileIsEmpty、往届记录的容器map
2. 在speechManager.cpp中实现成员函数void loadRecord()
void SpeechManager::loadRecord()
{
ifstream ifs("speech.csv", ios::in);//读文件
if (!ifs.is_open())
{
this->fileIsEmpty = true;
cout << "文件不存在" << endl;
ifs.close();
return;
}
//文件清空
char ch;
ifs >> ch;
if (ifs.eof())
{
cout << "文件为空" << endl;
this->fileIsEmpty = true;
ifs.close();
return;
}
//文件不为空
this->fileIsEmpty = false;
ifs.putback(ch);//将上面读取的单个字符再放回
string data;
while (ifs >> data)
{
cout << data << endl;
}
ifs.close();
}
3.测试? loadRecord()
构造函数加载记录,测试结果有两条往届记录:
while (ifs >> data)
{
//cout << data << endl;
//10002,86.375,10009,81,10010,78,
vector<string>v;//存放6个string字符串
int pos = -1;//查到","位置的变量
int start = 0;
while (true)
{
pos = data.find(",", start);
if (pos == -1)
{
//没有找到的情况
break;
}
string temp = data.substr(start, pos - start);
//cout << temp << endl;
v.push_back(temp);
start = pos + 1;
}
this->m_Record.insert(make_pair(index, v));
index++;
}
通过“,”查找分割每个数据,数据为编号、得分、编号、得分、编号、得分,并将查找结果进行记录到v中,m_Recoed记录:届数index+每届前三名得分情况v,循环读入每节届的得分情况。
1.speechManager.h中声明成员函数showRecord()
2.speechManager.cpp中实现成员函数showRecord()
3.测试showRecord()
测试结果:
目前程序中有几处bug未解决:
1.查看往届记录,若文件不存在或者为空,并未提示:
解决方式:在showRecord()函数中,判断文件状态
2.若记录为空或不存在,比赛后依然提示记录为空
解决方式:saveRecord()中更新文件为空标志
3.比玩赛后查找不到本届比赛的记录,没有实时更新
解决方式:比赛完毕后,所有数据重置
4.在初始化时,没有初始化记录容器
解决方式:initSpeech()中添加? 初始记录容器
5.每次记录都是一样的
解决方式:在main()函数一开始? 添加随机数种子
结果显示:
8.1 清空功能实现
1.在speeckManager.h中添加清空记录的成员函数void clearRecord();
2.在speeckManager.cpp中实现清空记录的成员函数void clearRecord();
8.2 清空功能测试
测试结果:
?