您的位置:首页 > 其它

ZOJ 3822 Domination(2014牡丹江Regional D题)

2014-10-12 22:52 302 查看
人家当场切掉的题,表示在场外做zoj还是要别人提醒dp数组的i,j,k分别表示什么含义才能AC...

下周鞍山之行无限堪忧TAT~

题目大意:有一个n * m的棋盘,每天放入一个棋子,当所有行和列都存在棋子的时候,就是一种符合的情况。

然后这种情况的值就是它的天数(也就是棋子个数),问所有符合的情况的期望值。

dp[i][j][k]表示放i个棋子,能盖住j行k列的概率。

由dp[i-1]也就是放i-1个棋子来推的话,如下图:


由这四种情况所推得的即为新的dp[i]。

代码如下:

#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
double dp[3000][55][55];
int t, n, m;
void init() {
memset(dp, 0, sizeof(dp));
dp[0][0][0] = 1.0;
}
int main() {
scanf("%d", &t);
while(t--) {
init();
scanf("%d%d", &n, &m);
if(n < m) swap(n, m);
int max_day = n * m - m + 1;
for(int i = 1; i <= max_day; i++) {
for(int j = 1; j <= i && j <= n; j++) {
for(int k = 1; k <= i && k <= m; k++) {
if(j == n && k == m) {
dp[i][j][k] = dp[i-1][j-1][k-1]*(double)(n-j+1)*(double)(m-k+1)/(double)(n*m-i+1)
+ dp[i-1][j][k-1]*(double)((m-k+1)*j)/(double)(n*m-i+1)
+ dp[i-1][j-1][k]*(double)((n-j+1)*k)/(double)(n*m-i+1);
} else {
dp[i][j][k] = dp[i-1][j-1][k-1]*(double)(n-j+1)*(double)(m-k+1)/(double)(n*m-i+1)
+ dp[i-1][j][k-1]*(double)((m-k+1)*j)/(double)(n*m-i+1)
+ dp[i-1][j-1][k]*(double)((n-j+1)*k)/(double)(n*m-i+1)
+ dp[i-1][j][k]*((double)(j*k)-(i-1))/(double)(n*m-i+1);
}
}
}
}
double ans = 0.0;
for(int i = 1; i <= max_day; i++) {
ans += double(i) * dp[i]
[m];
}
printf("%.10lf\n", ans);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: