@ysner
2018-08-05T12:24:42.000000Z
字数 1388
阅读 2895
DP
初始值为,现经过一段数,有的概率加上第个数。问最后值且加了个数的概率。
注意到都是没有意义的,于是可以把的范围视为。
直接设表示处理了第个数,加了个数,值为的概率。
决策就是是否加上这个数。
为了防止第三维变负,,空间要开到。
注意到因为有字节,下该数组会导致。
滚掉第一维即可。
复杂度(同阶)。
#include<iostream>#include<cstdio>#include<cstdlib>#include<cstring>#include<cmath>#include<algorithm>#include<vector>#define re register#define il inline#define ll long long#define max(a,b) ((a)>(b)?(a):(b))#define min(a,b) ((a)<(b)?(a):(b))#define fp(i,a,b) for(re int i=a;i<=b;i++)#define fq(i,a,b) for(re int i=a;i>=b;i--)using namespace std;const int mod=1e9+7,N=1e6+100;int n,l,k,sum;long double dp[2][205][410],ans;struct cha{int w;long double p;}a[N];il ll gi(){re ll x=0,t=1;re char ch=getchar();while(ch!='-'&&(ch<'0'||ch>'9')) ch=getchar();if(ch=='-') t=-1,ch=getchar();while(ch>='0'&&ch<='9') x=x*10+ch-48,ch=getchar();return x*t;}il int del(re int x){if(x>400) return 400;}int main(){freopen("guard.in","r",stdin);freopen("guard.out","w",stdout);n=gi();l=gi();k=gi();k=min(k+200,400);fp(i,1,n) scanf("%Lf",&a[i].p);fp(i,1,n) a[i].w=gi();re int now=1,nxt=0;fp(i,200,400) fp(j,l,n) dp[now][j][i]=1;fq(i,n,1){swap(now,nxt);memset(dp[now],0,sizeof(dp[now]));fp(j,0,i)fp(v,0,400){dp[now][j][v]+=a[i].p*dp[nxt][j+1][del(v+a[i].w)]/100;dp[now][j][v]+=(100-a[i].p)*dp[nxt][j][v]/100;}}printf("%.6Lf\n",dp[now][0][k]);fclose(stdin);fclose(stdout);return 0;}
