标题: | 1.5-1数字金字塔 |
详情: |
观察下面的数字金字塔。
写一个程序来查找从最高点到底部任意处结束的路径,使路径经过数字的和最大。每一步可以走到左下方的点也可以到达右下方的点。
7
3 8
8 1 0
2 7 4 4
4 5 2 6 5
|
http://bbs.codeaha.com/problem-12146.html
这题我一样用三种方式:普通dfs,记忆化dfs,和动态规划
1.普通dfs:
#include <cstdio> #include <algorithm> using namespace std; int a[1001][1001]={0},n,cnt; int dfs(int x,int y) { if (x==n)//边界值 { return a[x][y];返回 } return max(dfs(x+1,y),dfs(x+1,y+1))+a[x][y];//上面+右上角 } int main() { int i,j; scanf("%d",&n); for(i=1;i<=n;i++) { for(j=1;j<=i;j++) { scanf("%d",&a[i][j]); } } printf("%d",dfs(1,1)); return 0; }
2.记忆化dfs
#include <cstdio> #include <algorithm> using namespace std; int a[1001][1001]={0},n,cnt,f[1001][1001]={0}; int dfs(int x,int y) { if(f[x][y]==-1) { f[x][y]=max(dfs(x+1,y),dfs(x+1,y+1))+a[x][y];//记忆化 } return f[x][y];返回值 } int main() { int i,j; scanf("%d",&n); for(i=1;i<=n;i++) { for(j=1;j<=i;j++) { scanf("%d",&a[i][j]);//读入 f[i][j]=-1; } } for(i=1;i<=n;i++) f[n][i]=a[n][i]; printf("%d",dfs(1,1)); return 0; }
3.动态规划:
#include <cstdio> int main() { int n,a[1001][1001],d[1001][1001],i,j,k; scanf("%d",&n); for(i=1;i<=n;i++) { for(j=1;j<=i;j++) { scanf("%d",&d[i][j]); } } for(j=1;j<=n;j++) { a[n][j]=d[n][j]; } for(i=n-1;i>=1;i--) { for(j=1;j<=i;j++) { if(a[i+1][j+1]>a[i+1][j]) //分类 { a[i][j]=d[i][j]+a[i+1][j+1];选择右上角 } else { a[i][j]=d[i][j]+a[i+1][j];选择上面 } } } printf("%d",a[1][1]); return 0; }