poj 2948 Martian Mining (dp)

题目链接

完全自己想的,做了3个小时,刚开始一点思路没有,硬想了这么长时间,想了一个思路,

又修改了一下,提交本来没抱多大希望 居然1A了,感觉好激动。。很高兴dp又有所长进。

题意: 一个row*col的矩阵,每个格子内有两种矿yeyenum和bloggium,并且知道它们在每个

格子内的数量是多少。最北边有bloggium的收集站,最西边有 yeyenum 的收集站。

现在要在这些格子上面安装向北或者向西的传送带(每个格子自能装一种)。问最多能采到多少矿。

传送带只能直着走,不可弯曲,不能交叉。

分析:做题的时候一直在想状态转移 之间的关系,后来发现应该从左上角开始看起,每一个非零值的

格子,都要有一个传送的方向,因为是从上往下,从左往右的,所以前面的已经计算过了,所以方程

为d[i][j] = max(d[i-1][j]+ye[i][j], d[i][j-1]+bl[i][j]);

ye[i][j]表示从i行0列 到 i行j列的ye值, bl类似。

样例解释:

^     ^
< < < ^
< < < ^
< < < ^
 1 #include <iostream>
 2 #include <cstring>
 3 #include <cstdio>
 4 #include <algorithm>
 5 #define LL long long
 6 using namespace std;
 7 const int maxn = 500 + 10;
 8 int n, m, d[maxn][maxn], ye[maxn][maxn], bl[maxn][maxn];
 9 
10 int main()
11 {
12     int i, j, a;
13     while(~scanf("%d%d", &n, &m))
14     {
15         if(n==0 && m==0) break;
16         memset(d, 0, sizeof(d));
17         memset(ye, 0, sizeof(ye));
18         memset(bl, 0, sizeof(bl));
19         for(i = 1; i <= n; i++)
20         for(j = 1; j <= m; j++)
21         {
22             scanf("%d", &a);
23             ye[i][j] = ye[i][j-1] + a;
24         }
25         for(i = 1; i <= n; i++)
26         for(j = 1; j <= m; j++)
27         {
28             scanf("%d", &a);
29             bl[i][j] = bl[i-1][j] + a;
30         }
31         for(i = 1; i <= n; i++)
32         for(j = 1; j <= m; j++)
33         d[i][j] = max(d[i-1][j]+ye[i][j], d[i][j-1]+bl[i][j]);
34 
35         printf("%d
", d[n][m]);
36     }
37     return 0;
38 }
原文地址:https://www.cnblogs.com/bfshm/p/3804650.html