日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

CodeForces - 456D A Lot of Games(字典树+博弈)

發布時間:2024/4/11 编程问答 51 豆豆
生活随笔 收集整理的這篇文章主要介紹了 CodeForces - 456D A Lot of Games(字典树+博弈) 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

題目鏈接:點擊查看

題目大意:給出n個字符串,現在有兩個人玩一個游戲,游戲規則是兩人輪流構造同一個字符串,每次可以向末尾添加一個字母,必須保證添加字母后的字符串是n個字符串其中之一的前綴,不能操作者算輸,兩個人需要進行k次游戲,第一次游戲由先手開始,之后輸掉本局游戲的人為下一局游戲的先手,現在問誰能贏得最后一局的游戲

題目分析:考慮到需要對數量較大的前綴進行操作,我們可以使用字典樹來維護,這樣整個題目就變成了字典樹上的博弈,我們可以從葉子結點的狀態不斷向上轉移,最后轉移到字典樹的根節點,又因為字典樹的根節點是一個不存在的結點,所以我們對每個節點定義為:接下來一步的狀態,因為最后無法操作的人會輸掉比賽,所以葉子結點就是必敗態,要分清楚我們現在有四個狀態:

  • 必勝態
  • 必敗態
  • 可勝可敗態
  • 不可勝也不可敗態
  • 顯然狀態一二互斥,狀態三四互斥,這樣一來將狀態轉移到根節點然后分類討論就是答案了:

  • 先手必勝:則進行輪次為奇數時,先手獲勝,否則后手獲勝
  • 先手必敗:則先手必敗后下一局還是先手開始,會一直必敗,顯然后手獲勝
  • 可勝可敗:先手會故意讓自己一直輸,一直先手,最后一局的時候勝利,所以先手獲勝
  • 不可勝也不可敗:因為先手無論如何操作,下一次的操作權就交給后手了,此時后手就是可勝可敗態,同上面的第三條,所以后手獲勝
  • 代碼:

    #include<iostream> #include<cstdio> #include<string> #include<ctime> #include<cstring> #include<algorithm> #include<stack> #include<queue> #include<map> #include<set> #include<cmath> #include<sstream> #include<unordered_map> using namespace std;typedef long long LL;const int inf=0x3f3f3f3f;const int N=1e5+100;char s[N];int trie[N][26],cnt,val[N];void insert() {int pos=0;for(int i=0;s[i];i++){int to=s[i]-'a';if(!trie[pos][to])trie[pos][to]=++cnt;pos=trie[pos][to];} }void dfs(int pos)//val 1:必敗 2:必勝 3:可勝可敗 4:不能確定 {bool win=false;//必勝bool lose=false;//必敗 bool flag=true;//是否為子節點 for(int i=0;i<26;i++)if(trie[pos][i]){dfs(trie[pos][i]);if(val[trie[pos][i]]==1||val[trie[pos][i]]==4)win=true;if(val[trie[pos][i]]==2||val[trie[pos][i]]==4)lose=true; flag=false;}if(flag)val[pos]=1;else{if(win&&lose)val[pos]=3;else if(win)val[pos]=2;else if(lose)val[pos]=1;elseval[pos]=4;} }int main() { // freopen("input.txt","r",stdin); // ios::sync_with_stdio(false);int n,m;scanf("%d%d",&n,&m);while(n--){scanf("%s",s);insert();}dfs(0);if(val[0]==1){puts("Second");}else if(val[0]==2){if(m&1)puts("First");elseputs("Second");}else if(val[0]==3){puts("First");}else{puts("Second");}return 0; }

    ?

    總結

    以上是生活随笔為你收集整理的CodeForces - 456D A Lot of Games(字典树+博弈)的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。