Problem C. Board Game Google Kickstart Round E 2018
阿新 • • 發佈:2018-11-09
題意:A與B各有3N個卡片,每場game時A隨機把卡片分到3個battlefield裡面。每個battlefield裡如果A的卡片integer之和>=B的卡片integer之和,則A贏,反之B贏。贏的battlefield多的一方贏了這場game。問B在最優策略下平均贏幾場比賽(期望值)。
small input N=3,每個battlefield裡面卡片是無序的,所以一共有C(9,3)*C(6,3)*C(3,3)=1680種可能。dfs預處理枚舉出這些組合,找到B的一種組合,使得其對於A的所有組合贏的期望值最大。
#include<iostream> #include<stdio.h> #include<cstdio> #include<string> #include<cmath> #include<stdlib.h> #include<algorithm> #include<string.h> #include<cstring> #include<vector> #include<queue> #include<map> #include<set> #include<ctime> using namespace std; const int maxn=10; const int maxl=1680; int T; int N=3; int A[maxn]; int B[maxn]; int used[maxn]; int mp[3][3]; int cnt=0; vector<int>comb[maxl]; double ans; void dfs(int x,int y,int st) { if(x>=3) { // cnt++; for(int i=0;i<3;i++) { for(int j=0;j<N;j++) { // cout<<mp[i][j]<<" "; comb[cnt].push_back(mp[i][j]); } } // cout<<endl; cnt++; return; } if(y>=N) { dfs(x+1,0,0); } for(int i=st;i<3*N;i++) { if(used[i])continue; mp[x][y]=i; used[i]=1; dfs(x,y+1,i+1); used[i]=0; } } int main() { // freopen("input.txt","r",stdin); freopen("C-small-attempt0.in","r",stdin); freopen("C-small.txt","w",stdout); clock_t START_TIME; clock_t FINISH_TIME; START_TIME=clock(); scanf("%d",&T); memset(mp,0,sizeof(mp)); memset(used,0,sizeof(used)); dfs(0,0,0); for(int ca=1;ca<=T;ca++) { scanf("%d",&N); memset(A,0,sizeof(A)); memset(B,0,sizeof(B)); ans=0; for(int i=0;i<3*N;i++) { scanf("%d",&A[i]); } for(int i=0;i<3*N;i++) { scanf("%d",&B[i]); } // for(int i=0;i<3*N;i++) // { // cout<<A[i]<<" "; // } // cout<<endl; // for(int i=0;i<3*N;i++) // { // cout<<B[i]<<" "; // } // cout<<endl; // return 0; // vector<int>opt{0,1,2,3,4,7,5,6,8}; // vector<int>opt2{0,1,2,3,4,7,5,6,8}; // cout<<(opt==opt2)<<endl; // for(int i=0;i<opt.size();i++) // { // cout<<opt[i]<<endl; // } for(int i=0;i<cnt;i++) { int final_win=0; for(int j=0;j<cnt;j++) { int win=0;//for bahu for(int k=0;k<3*N;k+=N) { int sumA=0; int sumB=0; for(int l=k;l<k+N;l++) { sumA+=A[comb[i][l]]; sumB+=B[comb[j][l]]; // if(comb[i]==opt) // { // cout<<"A "<<A[comb[i][l]]<<endl; // cout<<"B "<<B[comb[j][l]]<<endl; // } } if(sumA>sumB) { win++; } // if(comb[i]==opt) // { // cout<<k<<" "<<sumA<<" "<<sumB<<endl; // } } if(win>=2) { final_win++; } // if(comb[i]==opt) // { // cout<<win<<" "<<final_win<<endl; // } } // if(comb[i]==opt) // { // return 0; // } // if(final_win==1680) // { // cout<<final_win<<endl; // } ans=max(ans,1.0*final_win/cnt); } printf("Case #%d: %.7f\n",ca,ans); cerr<<"finish case "<<ca<<endl; } FINISH_TIME=clock(); cerr<<1.0*(FINISH_TIME-START_TIME)/CLOCKS_PER_SEC <<" (s) "<<endl; return 0; }