1. 程式人生 > >1418:猴子選大王

1418:猴子選大王

題目連線:http://ybt.ssoier.cn:8088/problem_show.php?pid=1418

  從佇列到迴圈單鏈表寫了一下午都寫不出來,網上查了半天題解發現多數用到<vector>而且還用到迭代器(https://blog.csdn.net/u011954296/article/details/51351982),對於我那群沒學過的娃來說比較難理解,還有用牛逼的數學公式推到出來只用20行程式碼就解決問題,反正我是想不到。晚間在家看孩子時,靈光一現,這個是不是可以用“雙向迴圈連結串列”就可以克服下午遇到的種種問題,於是迅速花半個小時寫出,程式碼很短,理解“雙向迴圈連結串列”就很容寫出了,加上詳細註釋,獨家出品,如有雷同罰款100,僅供參考。但個人還是覺得這種數學的推理是值得推介的(

https://www.cnblogs.com/jiu0821/p/4587507.html),一題多解,解後看別人題解,一定是提升演算法學習非常有效的學習方法,建議大家多多看看別人的程式碼。

 1 #include<iostream>
 2 using namespace std;
 3 struct node{
 4     int pre;//儲存之前節點下標 
 5     int x;//當前可以數得數 
 6     int nex;//儲存之後節點下標 
 7 }q[1000100];//自定義迴圈雙向連結串列的資料結構
 8             //思考為什麼不能用單向迴圈連結串列??? 
 9 int
main() 10 { 11 int n; 12 cin>>n; 13 for(int i=1; i<=n; i++)//構造迴圈雙向連結串列 14 { 15 cin>>q[i].x; 16 if(i==n) q[i].nex=1; 17 else q[i].nex=i+1; 18 if(i==1) q[i].pre=n; 19 else q[i].pre=i-1; 20 } 21 //for(int i=1; i<=n; i++)cout<<q[i].pre<<q[i].x<<q[i].nex<<endl;
//用於測試構造的迴圈雙向連結串列是否成功 22 int now=1;//從第一隻猴子開始 23 while(q[now].nex!=now && q[now].pre!=now)//當只剩下最後一隻猴子時,他的之前節點和之後節點都指向它自己,於是他就是大王 24 { 25 int xx=now, yy=q[now].x;//當前開始計數的猴子編號 26 for(int i=xx; i<xx+yy-1; i++) now=q[now].nex; // 從當前猴子的節點開始報數到<被刪除猴子>的節點,此時now為 <被刪除猴子>的節點的下標 27 28 q[q[now].pre].nex=q[now].nex;//<被刪除猴子>之前節點的之後節點更改為<被刪除猴子>的之後節點 29 q[q[now].nex].pre=q[now].pre;//<被刪除猴子>之後節點的之前節點更改為<被刪除猴子>的之前節點 30 31 now=q[now].nex;//更改now為刪除猴子的下一個節點重複 32 33 } 34 cout<<now; 35 return 0; 36 }

AC後開心的去睡覺覺~~~