题意:n种病毒,s个系统 每次能在某个系统下发现某个病毒,求发现n种病毒&&每个系统至少发现一个病毒所需要的期望次数?
令d[i][j]表示当前发现了i种病毒&&发现j个系统中至少有一个病毒时,离目标(n,s)所需要的期望次数
然后根据E(aA+bB+cC+dD+...)=aEA+bEB+....;//a,b,c,d...表示概率,A,B,C...表示状态
每次有4种情况
已发现系统找到同一种病毒,概率为:p1=(i/n)*(j/s)
没发现系统中找到同一种病毒,p2=(i/n)*((s-j)/s)
已发现系统中找到不同种病毒 p3=((n-i)/n)*(j/s)
没发现系统中找到不同种病毒 p4=((n-i/n))*((s-j)/s)
d[i][j]=1+p1*d[i][j]+p2*dp[i][j+1]+p3*dp[i+1][j]+p4*dp[i+1][j+1]
d[i][j]移项: d[i][j]=(1+p2*dp[i][j+1]+p3*dp[i+1][j]+p4*dp[i+1][j+1])/(1-p1)
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
typedef long long ll;
const ll inf=1e15;
const int N=2e3+50;
int n,s;
double dp[N][N];
int main()
{
while(cin>>n>>s)
{
memset(dp,0,sizeof(dp));
for(int i=n;i>=0;i--)
{
for(int j=s;j>=0;j--)
{
if(i==n&&j==s) continue;
double p=1.0-(double)(i*j)/(n*s);
dp[i][j] += (double) (n - i) * (s - j) / (n * s) * dp[i+1][j+1];
dp[i][j] += (double) i * (s-j) / (n * s) * dp[i][j+1];
dp[i][j] += (double) (n - i) * j / (n * s) * dp[i+1][j];
dp[i][j]=(dp[i][j]+1.0)/p;
}
}
printf("%.4lf\n",dp[0][0]);
}
return 0;
}