一道典型的题很难读懂
读懂我也做不起的题
看了一下题解
大抵是照着打出来了
表示前i个卡片有严格j张生效的期望概率
转移是这样的
这是啥子意思:由于一张牌只能用一次
一个轮中假设用了j-1张剩下的有r-j的次数会考虑第i张
则有选和不选两种转移
最后统计每种的概率是相同的
#include<bits/stdc++.h>
using namespace std;
double F[251][251];
double G[251];
double p[251];
double d[251];
int n,r;
double quick_pow(double x,int k){
double ret=1.0;
while(k){
if(k%2==1){
ret=ret*x;
}
k/=2;
x=x*x;
}
return ret;
}
int main(){
// freopen("P3239.in","r",stdin);
int Cas;
scanf("%d",&Cas);
while(Cas--){
memset(F,0,sizeof(F));
memset(G,0,sizeof(G));
scanf("%d%d",&n,&r);
for(int i=1;i<=n;i++){
scanf("%lf%lf",&p[i],&d[i]);
}
F[1][0]=quick_pow(1.0-p[1],r);
F[1][1]=G[1]=1.0-quick_pow(1.0-p[1],r);
for(int i=2;i<=n;i++){
for(int j=0;j<=min(i,r);j++){
if(j)F[i][j]+=F[i-1][j-1]*(1.0-quick_pow(1.0-p[i],r-j+1));
if(i!=j)F[i][j]+=F[i-1][j]*quick_pow(1.0-p[i],r-j);
}
}
for(int i=2;i<=n;i++){
for(int j=0;j<=min(i-1,r);j++){
G[i]+=F[i-1][j]*(1.0-quick_pow(1.0-p[i],r-j));
}
}
double ans=0;
for(int i=1;i<=n;i++)ans+=d[i]*G[i];
printf("%.10lf\n",ans);
}
}