题意:打败1个tour可以获得奖品或者是一个袋子,一开始自己拿了一个容量为k的袋子,打败某个tour的概率是p,问一个人可以至少打败L个tour和把自己所有奖品拿回去的概率。
做法:建立状态dp[i][j][k],在前i个tour,打败j个,剩下k的容量。没看见那个instead,错了许久,原来有些tour只会给你个袋子啊...
#include <iostream>
#include<cstdio>
#include<algorithm>
using namespace std;
const int LMT=202;
const int zero=200;
int rest[LMT];
double dp[LMT][LMT][LMT<<1],p[LMT];
int main()
{
int n,l,k,x;
double ans=0;
scanf("%d%d%d",&n,&l,&k);;
for(int i=1;i<=n;i++)
{
scanf("%d",&x);
p[i]=x/100.0;
}
for(int i=1;i<=n;i++)
{
scanf("%d",&rest[i]);
}
const int end=zero+200;
dp[0][0][zero+k]=1;
for(int i=1;i<=n;i++)
for(int j=0;j<i;j++)
for(int k=0;k<=end;k++)
{
if(rest[i]!=-1)
{
int x=min(end,k+rest[i]);
dp[i][j+1][x]+=dp[i-1][j][k]*p[i];
}
else if(k>0)dp[i][j+1][k-1]+=dp[i-1][j][k]*p[i];
dp[i][j][k]+=dp[i-1][j][k]*(1-p[i]);
}
for(int i=l;i<=n;i++)
for(int j=zero;j<=end;j++)
ans+=dp[n][i][j];
printf("%.12lf\n",ans);
return 0;
}