標籤:
題意:
你有X元錢,進行M輪賭博遊戲。每一輪可以將所持的任意一部分錢作為賭注(賭注為0元表示這一輪不押),賭注可以是小數的,不是一定要整數。每一輪 贏的機率為P,贏了賭注翻倍,輸了賭注就沒了。如果你最後持有至少1000000元錢的話,就可以把錢全部帶走。要求計算在採取最優策略時,獲得至少 1000000元錢的機率。
資料範圍:
0<=P<=1
1<=X<=1000000
1<=M<=15
1 int M , X ; 2 double P; 3 double dp[2][(1 << 15) + 1]; 4 void solve() 5 { 6 int n = 1 << M; 7 double *pre = dp[0] , *nxt = dp[1]; 8 memset(pre , 0 , sizeof(double) * (n + 1)); 9 /// memset(pre , 0 , sizeof(pre)); 這樣初始化是不行的,因為pre為一個double型的指標,不是整個數組。 10 pre[n] = 1.0; 11 for(int r = 0 ; r < M; r++)///枚舉第幾輪 12 { 13 for(int i = 0 ; i <= n ; i++)///枚舉當前是哪種狀態 14 { 15 int step = min(i , n - i);///如果step大於n / 2 , 等會兒轉移的時候可能會超過n 16 double t = 0.0; 17 for(int j = 0 ; j <= step ; j++)///枚舉當前的所有可能走法 18 { 19 t = max(t , P * pre[i + j] + (1 - P) * pre[i - j]);///求出期望的最大值 20 } 21 nxt[i] = t; 22 } 23 swap(pre , nxt);///交換兩個數組的值進行滾動 24 } 25 int i = (LL)X * n / 1000000;///找到X對應的是第幾塊 26 // for(int i = 0 ; i <= n ; i++)cout << ‘*‘ << pre[i] << endl; 27 printf("%.6lf\n" , pre[i]); 28 }
Code Jam 2008 APAC local onsites Problem C. Millionaire —— 機率DP