//下面是错误代码...
1 #include "iostream" 2 #include "cstdio" 3 #include "cstring" 4 #include "algorithm" 5 #include "cmath" 6 using namespace std; 7 const double eps = 1e-5; 8 double dp[1010][1010]; 9 int R, C; 10 double p[1010][1010][3]; 11 bool cant[1010][1010]; 12 13 int main() 14 { 15 int i, j, k; 16 while(scanf("%d%d", &R, &C)!=EOF) { 17 memset(dp, 0, sizeof(dp)); 18 memset(cant, 0, sizeof(cant)); 19 for(i = 1; i <= R; ++i) { 20 for(j = 1; j <= C; ++j) { 21 scanf("%lf%lf%lf", &p[i][j][0], &p[i][j][1], &p[i][j][2]); 22 if(fabs(p[i][j][0] - 1.0) > eps) { 23 dp[i][j] = (dp[i][j - 1] + 2) * p[i][j - 1][1] + (dp[i - 1][j] + 2) * p[i - 1][j][2] + 2 * p[i][j][0]; 24 dp[i][j] /= (1 - p[i][j][0]); 25 if(j==1) 26 cant[i][j - 1] = 1; 27 if(i==1) 28 cant[i - 1][j] = 1; 29 30 if(cant[i][j - 1] && cant[i - 1][j] && (i != 1 || j != 1)) 31 cant[i][j] = 1, dp[i][j] = 0; 32 } 33 else 34 cant[i][j] = 1, dp[i][j] = 0; 35 //printf("%d %d dp[%d][%d] == %f ",cant[i][j - 1], cant[i - 1][j], i, j, dp[i][j]); 36 } 37 } 38 dp[R][C] = 0; 39 if(!cant[R][C - 1]) 40 dp[R][C] += (dp[R][C - 1] + 2) * p[R][C - 1][1]; 41 if(!cant[R - 1][C]) 42 dp[R][C] += (dp[R - 1][C] + 2) * p[R - 1][C][2]; 43 printf("%.3f ", dp[R][C]); 44 } 45 }
//对拍之后发现,上面的程序和标程的输出差的好远好远,所以一定是计算公式错了...
//生成随机数据的程序
1 #include "iostream" 2 #include "cstdio" 3 #include "cstring" 4 #include "algorithm" 5 #include "ctime" 6 using namespace std; 7 void Print() 8 { 9 int tot = 100, i; 10 for(i = 1; i <= 2; i++) { 11 if(tot == 0) { 12 printf("0 "); 13 continue; 14 } 15 int tmp = rand() % (tot + 1); 16 printf("%f ", (double)tmp / 100.0); 17 tot -= tmp; 18 } 19 printf("%f ", (double)tot / 100.0); 20 } 21 22 int main() 23 { 24 srand(time(NULL)); 25 freopen("input.txt", "w", stdout); 26 int i, j, r, c; 27 r = 10,c = 21; 28 printf("%d %d ", r, c); 29 for(i = 1; i <= r; ++i) { 30 for(j = 1; j <= c; ++j) { 31 Print(); 32 } 33 } 34 }
//期望 = 概率 * 取值,所以这题的状态转移方程其实在一开始就确定了...,自己相当然的去设计转移方程就会陷入误区
//正确的代码
1 #include "iostream" 2 #include "cstdio" 3 #include "cstring" 4 #include "algorithm" 5 #include "cmath" 6 using namespace std; 7 const double eps = 1e-5; 8 int r, c; 9 double dp[1010][1010], p[1010][1010][3]; 10 11 int main() 12 { 13 int i, j, k; 14 while(scanf("%d%d", &r, &c) != EOF) { 15 for(i = 1; i <= r; ++i) 16 for(j = 1; j <= c; ++j) 17 for(k = 0; k <= 2; ++k) 18 scanf("%lf", &p[i][j][k]); 19 memset(dp, 0, sizeof(dp)); 20 for(i = r; i >= 1; --i) { 21 for(j = c; j >= 1; --j) { 22 if(i == r && j == c) 23 continue; 24 if(fabs(p[i][j][0] - 1) < eps) 25 continue; 26 dp[i][j] = (dp[i][j + 1] + 2) * p[i][j][1] + (dp[i + 1][j] + 2) * p[i][j][2] + 2 * p[i][j][0]; 27 dp[i][j] /= (1 - p[i][j][0]); 28 } 29 } 30 printf("%.3f ", dp[1][1]); 31 } 32 }
//记忆化搜索
1 #include "iostream" 2 #include "cstdio" 3 #include "cstring" 4 #include "algorithm" 5 #include "cmath" 6 using namespace std; 7 const double eps = 1e-5; 8 int r, c; 9 double dp[1010][1010], p[1010][1010][3]; 10 bool vis[1010][1010]; 11 double dfs(int row, int col) 12 { 13 if(vis[row][col]) 14 return dp[row][col]; 15 vis[row][col] = 1; 16 if(row <= 0 || row > r || col <= 0 || col > c || fabs(p[row][col][0] - 1) < eps) 17 return dp[row][col] = 0; 18 else { 19 dp[row][col] = p[row][col][1] * (dfs(row, col + 1) + 2) + p[row][col][2] * (dfs(row + 1, col) + 2) + p[row][col][0] * 2; 20 dp[row][col] /= 1 - p[row][col][0]; 21 } 22 return dp[row][col]; 23 } 24 25 int main() 26 { 27 int i, j, k; 28 while(scanf("%d%d", &r, &c) != EOF) { 29 for(i = 1; i <= r; ++i) 30 for(j = 1; j <= c; ++j) 31 for(k = 0; k <= 2; ++k) 32 scanf("%lf", &p[i][j][k]); 33 memset(dp, 0, sizeof(dp)); 34 memset(vis, 0, sizeof(vis)); 35 printf("%.3f ", dfs(1, 1)); 36 } 37 }