首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> C++ >> 關於C++

Codeforces Round #304 Div.2 C:Soldier and Cards 模擬與集合去重

     編輯:關於C++

問題描述

兩人分 n≤10 張牌(1..n 各一張),輪流出牌比大,大者將兩張牌置於自己牌堆底(先對手牌後自己牌)。一方牌盡則輸。求回合數與贏家,或判定無限循環(輸出 -1)。

解法:直接模擬 + 狀態記錄

  • 用 queue 表示雙方牌堆。
  • 每回合取隊首比較,按規則入隊。
  • 狀態 = 兩個隊列序列。用 set, queue>> 記錄已見狀態(C++ queue 支持比較運算符)。
  • 若重複狀態出現,輸出 -1。否則最多 10! 狀態,但實際極快收斂,官方說明步數不超過 1e6。

代碼


queue q[2];
set, queue>> seen;
int main() {
    int n; while(cin>>n) {
        seen.clear(); q[0]=q[1]=queue();
        for(int i=0;i<2;i++) { int k,x; cin>>k; while(k--){cin>>x;q[i].push(x);} }
        seen.insert({q[0],q[1]});
        int step=0;
        while(!q[0].empty() && !q[1].empty()) {
            int a=q[0].front();q[0].pop();
            int b=q[1].front();q[1].pop();
            if(a

複雜度

狀態數上界 n! * (n+1)(分割點),n=10 時 ~4e7,但實際測試極快。集合查找 O(log S),S 為已見狀態數。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved