1. 程式人生 > >ZOJ 3640 Help Me Escape 概率dp

ZOJ 3640 Help Me Escape 概率dp

題目大意:

人需要逃出地洞,每個地洞有自己的守衛者。守護者的戰力為c[i]。

每天人會被隨機的分配到一個地洞的出口前。

當人的戰力值f>c[i]時花費天即可逃出。

否則,戰力值加上c[i],天數加一,第二天隨機出現在一個地洞口。

問逃出去的天數的期望值。

題目分析:

分類討論

d[i]是武力值為i的時候逃出地洞需要天數的期望值。

1.i> c[j] , d[i] += floor(1+sqrt(5.0))/2 *c[i]^2/n

2.i <= c[j] ,d[i] +=(d(i+c[i])+1)/n

答案就是d[f]

#include <bits/stdc++.h>
using namespace std;
#define N 20005
double d[N];
double c[N];
double p = 0.5+sqrt(5.0)/2;
int n,f;
double dp(int tf){
    //if(tf>N)tf = N-1;
    if(d[tf]>0)return d[tf];
    for(int i=0;i<n;i++){
        if(tf>c[i]){
            d[tf]+=floor(p*c[i]*c[i])/n;
        }else {
            d[tf]+=(dp(tf+c[i])+1)/n;
        }
    }
    return d[tf];
}
int main(){
    //std::ios::sync_with_stdio(false);
    while(cin>>n>>f){
        for(int i=0;i<n;i++){
            cin>>c[i];
        }
        memset(d,0,sizeof(d));
        printf("%.3f\n",dp(f));
    }
}