軟體工程-構建之法 黃金點小遊戲

來源:互聯網
上載者:User

標籤:

一、背景

黃金點遊戲是一個數字小遊戲,其遊戲規則是:

      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輪以上,並能夠保留各輪比賽結果。

二、分析

     這個小遊戲,你肯定會想, 如果大家隨機報數的話,  

第一輪開始:可能是真正的隨機,0-100 的平均數是50,  50 * 0.618 = 31.   那我就來個 31。

第二輪開始:當大家漸漸明白了遊戲的BUG時候,但 他們肯定也想到選31附近,如果大家大家都選 31 附近的數,  那我得選 31*0.618 = 19; 

第三輪以及之後的。。。。。。

 

但是這些人肯定也想到了這一點,  那我要選 19 * 0.618 = 12…   然後 12 * 0.618 = 8

。。。。。。。。

最後乾脆選越小的數,例如0.00000000001,這是個有理數。

 

0.00000000001是正確答案麼?  這取決於參與遊戲的所有成員。

 

當這個遊戲的人員都是程式員或者都是智商比較高的人員,遊戲的確會出現我們之前預測的一樣,G點的值在不斷的下降。

 

但是如果是一群知識為了開心的玩耍的小夥伴呢,那麼這個結果就會出現各種情況,結果不具有預見性,但是你仔細觀察會發現,G值的大小不是由少數人決定的,而是由大多數人決定的。最恐怖是反向逆行的遊戲者最後都“守約” 提交了大數,最終你的分數是負數,再來一輪,你也不是傻瓜,你也會使自己的數足夠的小,走出自己是-2分的局面。

 

黃金比例0.618,在生活中,學習都可以經常見到,黃金比例分割是指把一條線段分割為兩部分,使其中一部分與全長之比等於另一部分與這部分之比。其比值是一個無理數,取其前三位元字的近似值是0.618。所謂黃金分割,指的是把長為L的線段分為兩部分,使其中一部分對於全部之比,等於另一部分對於該部分之比。而計算黃金分割最簡單的方法,是計算斐波那契數列1,1,2,3,5,8,13,21,...後二數之比2/3,3/5,4/8,8/13,13/21,...近似值的。

 

三、易錯點

之前自己認為是整數,當自己輸入時有理數時候程式自動停止。當程式中出現中國人的名字的時候時候可以儲存,當map中沒有清空。。。。。。。。。

易出現的錯誤(1):是有理數,不是整數

原因及解決辦法:改變map<string,int>mp;--->map<string,double>mp;這個就是map非常靈活的地方,自己可以自己定義資料類型。

易出現的錯誤(2):當遊戲人數不變時,人員發生改變時,大家還是可以繼續玩

原因及解決辦法:每一次的求和,平均值,G值清空。

易出現的錯誤(3):當人員名字改變時,每一輪的遊戲開始都是新的開始

解決原因及辦法:自己的map每一次都沒有清空,使用的map中的函數clear(),語句是使用mp.clear()清空。

當第一輪中的人員和第二輪中的人員不一樣時,map中存了所欲哦

易錯點(4):每一輪的輸入可不可以不按照一定順序的輸入,但是map最終是以map字典序的輸出,

原因及解決辦法:map還有一個優點是自動對第一個欄位進行排序。所以在遊戲中可以可以當有的人還沒有想好交上什麼資料,可以跳過,不會影響到結果的。

大家選取的資料越來越小的時候,會出現G值的確會逐漸減小。

四、結對程式設計的照片(Ps:認真帥氣漂亮)

   

  

五、總結和評價

      這一次結對程式設計,可以說不是自己的第一次結對程式設計,在ACM中經常就是一個編程,一個人複審,另外一個人提供思路,然後交叉輪流編程,輪流代碼審核,這樣編程效率高,還不容易出錯,而且可以通過結對程式設計,熟悉瞭解搭檔的編程風格和思路模式,也是對自己的不足的地方一種提高。是一種相互學習的方式,只會讓結對程式設計的兩人的編程水平共同提高,但是存在這樣的情況,你壓根不想和他一起編程,只會讓彼此相互埋汰,然後工作效率低。

     對隊友的評價:在明白題意後,自己的思路是使用STL中的Map,時間複雜度logn,我先把map建立與資料的輸入進行簡單的測試,然後再把寫到多輪遊戲的開始完成。但是她給我提出一個如果要顯示多輪之後的成績怎麼顯示,她說,他可以定義另外一個map的變數,用來存每一次的分數,在累加,就可以實現。

六、原始碼(使用的軟體Code Block,在GCC編譯器編譯通過)

#include <iostream>#include<cstdio>#include<cstdlib>#include<map>using namespace std;int main(){    int game_num;    map<string,double>mp;    int i,n;    double num,sum,ave;    int 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--;        }    }    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 =(int)abs(G-(int)iter->second);    //iter存的是差值              }    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;}

如果文中存在錯誤,請幫忙指出,大家可以一起討論,共同提高。

資料

 

軟體工程-構建之法 黃金點小遊戲

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.