一.关于游戏
黄金点游戏是一个数字小游戏,其游戏规则是:
N个同学(N通常大于10),每人写一个0~100之间的有理数 (不包括0或100),交给裁判,裁判算出所有数字的平均值,然后乘以0.618(所谓黄金分割常数),得到G值。提交的数字最靠近G(取绝对值)的同学得到N分,离G最远的同学得到-2分,其他同学得0分。玩了几天以后,大家发现了一些很有意思的现象,比如黄金点在逐渐地往下移动。
现在请大家根据这个游戏规则,编一个可以多人一起玩的小游戏程序,要求如下:
1、本作业属于结对编程项目,必须由二人共同完成,并分别将本次作业过程发到博客,同时将本次作业源代码提交到codeing系统;
2、如果可能的话尽量以C/S或B/S方式实现,即利用服务器接收和处理所有玩家提交的数字,并将结果反馈给各玩家,玩家可以通过客户端提交的数字;
3、如果采用单机方式实现的话,需要为用户提供便利的输入界面;
4、该游戏每次至少可以运行10轮以上,并能够保留各轮比赛结果。
二.关于代码
1.首先我们选择用c++来编写程序。
本来考虑用数组来存储要输入的信息,又考虑到会比较繁琐就选择了用c++中的map。在主函数中用map容器来存储游戏的人名和输入的数字。用while循环控制循环次数,每轮游戏结束后用mp.clear()清空数据。具体程序如下。
int main() { int game_num; map<string,double>mp; int i,n; double num,sum,ave; double G,temp=0; string name; printf("请输入游戏的人数:"); scanf("%d",&n); printf("\n"); printf("请输入此次游戏进行的轮数:"); scanf("%d",&game_num); printf("\n"); while(game_num--) { ++temp; mp.clear(); //清空map中的数据 sum=0;ave=0;G=0; printf("第%d轮开始:\n",temp); printf("请输入每人的姓名和有理数(空格隔开):\n"); for(i=0;i<n;i++) { cin>>name>>num; if(num>0.0&&num<100.0) { mp[name]=num; //建立map的关系 sum=sum+num; } else { printf("请输入(0-100)的有理数\n"); i--; } }
2.接下来计算总和,平均值以及G点值。用iter->first存参与游戏的人的名字,iter->second存每一个人的数字,然后将每个人输入的数字跟G点的差值的绝对值存入iter中,并将mp中的值更新,从开始mp.begin()到mp.end()比较大小,将最大值放入result_high中,将最小值放到result_high中,输出结果差值最大的得到-2分,差值最小的得到n分,n是参与游戏的人数。其余人都赋予0分,输出每个人的名字以及得分。具体程序如下。
printf("总和为:%.4lf\n",sum); ave=sum/n; printf("平均值:%.4lf\n",ave); G=ave*0.618; printf("G点值:%.4lf\n",G); for(iter=mp.begin();iter!=mp.end();iter++) { iter->second =(double)fabs(G-(double)iter->second); //fabs函数是double的绝对值 } for(iter=mp.begin(),result_high=mp.begin(),result_low=mp.begin();iter!=mp.end();iter++) { if(iter->second<result_high->second) result_high=iter; if(iter->second>result_low->second) result_low=iter; } cout<<endl; cout<<"姓名"<<"\t"<<"差值"<<endl; cout<<result_high->first<<"\t"<<result_high->second<<"\t"<<"得到"<<n<<"分"<<endl; cout<<result_low->first<<"\t"<<result_low->second<<"\t"<<"得到-2分"<<endl; cout<<endl; for(iter=mp.begin();iter!=mp.end();iter++) { iter->second =0; } for(iter=mp.begin();iter!=mp.end();iter++) { if(iter==result_high) iter->second+=n; if(iter==result_low) iter->second+=-2; } cout<<"第"<<temp<<"轮结果:"<<endl; cout<<"姓名"<<"\t"<<"分数"<<endl; for(iter=mp.begin();iter!=mp.end();iter++) cout<<iter->first<<"\t"<<iter->second<<endl; cout<<endl;
3.关于map
map是c++的一个标准容器,提供了很好的一对一关系,在一些程序中建立一个map可以起到事半功倍的效果。
map是一类关联式容器,使用map得包含map累所在的头文件,在编程时还用到了几个map的关键字。
map<string,double>mp//map的定义
#include<map>//头文件
begin()
end()
clear()//清空
4.程序运行结果
三.关于结对编程
这次的编程要求是需要两个人结对编程,共同完成整个程序的设计和编写。我的编程队友是程新松,他是一个认真又好学的人,跟他结对编程能够学到很多东西,他的编程能力比较强,而我的编程能力较弱,很多东西都是在他的帮助指导下完成的,在此表示感谢。另外在编程过程中我也收获了很多,希望以后有机会还可以共同学习。
附上工作照片一张:
四.程序代码
#include <iostream>
#include<cstdio>
#include<cstdlib>
#include<map>
#include<math.h>
using namespace std;
int main()
{
int game_num;
map<string,double>mp;
int i,n;
double num,sum,ave,G;
int temp=0;
string name;
printf("请输入游戏的人数:");
scanf("%d",&n);
printf("\n");
printf("请输入此次游戏进行的轮数:");
scanf("%d",&game_num);
printf("\n");
while(game_num--)
{
++temp;
mp.clear(); //清空map中的数据
sum=0;ave=0;G=0;
printf("第%d轮开始:\n",temp);
printf("请输入每人的姓名和有理数(空格隔开):\n");
for(i=0;i<n;i++)
{
cin>>name>>num;
if(num>0.0&&num<100.0)
{
mp[name]=num; //建立map的关系
sum=sum+num;
}
else
{
printf("请输入(0-100)的有理数\n");
i--;
}
}
map<string,double>::iterator iter,result_high,result_low;
printf("总和为:%.4lf\n",sum);
ave=sum/n;
printf("平均值:%.4lf\n",ave);
G=ave*0.618;
printf("G点值:%.4lf\n",G);
for(iter=mp.begin();iter!=mp.end();iter++)
{
iter->second =(double)fabs(G-(double)iter->second);
}
for(iter=mp.begin(),result_high=mp.begin(),result_low=mp.begin();iter!=mp.end();iter++)
{
if(iter->second<result_high->second)
result_high=iter;
if(iter->second>result_low->second)
result_low=iter;
}
cout<<endl;
cout<<"姓名"<<"\t"<<"差值"<<endl;
cout<<result_high->first<<"\t"<<result_high->second<<"\t"<<"得到"<<n<<"分"<<endl;
cout<<result_low->first<<"\t"<<result_low->second<<"\t"<<"得到-2分"<<endl;
cout<<endl;
for(iter=mp.begin();iter!=mp.end();iter++)
{
iter->second =0;
}
for(iter=mp.begin();iter!=mp.end();iter++)
{
if(iter==result_high)
iter->second+=n;
if(iter==result_low)
iter->second+=-2;
}
cout<<"第"<<temp<<"轮结果:"<<endl;
cout<<"姓名"<<"\t"<<"分数"<<endl;
for(iter=mp.begin();iter!=mp.end();iter++)
cout<<iter->first<<"\t"<<iter->second<<endl;
cout<<endl;
}
return 0;
}