这个题就是数塔问题。比较简单。 要记录路径。 每次保存一个位置的上一个位置就行。
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <string>
#include <algorithm>
#include <fstream>
#include <set>
#include <map>
#include <queue>
#include <stack>
#include <list>
#include <vector>
#include <cmath>
#include <iomanip>
typedef long long LL;
typedef unsigned long long LLU;
const double PI=acos(-1.0);
using namespace std;
#define MAXN 100+10
#define INF 1 << 30
int f[MAXN][MAXN] = {0};
void dfs(int i, int j){
if(i == 2){
printf("%d ",f[i][j]);
return ;
}
else{
dfs(i-1,f[i][j]);
printf("%d ",f[i][j]);
return;
}
}
int main()
{
int t;
int kase = 0;
scanf("%d",&t);
while(t--){
int m,n;
int wh[MAXN][MAXN] = {0};
memset(f,0,sizeof(f));
int d[MAXN][MAXN] = {0};
scanf("%d%d",&m,&n);
for(int i =1; i <= m; i++)
for(int j = 1; j <= n; j++)
scanf("%d",&wh[i][j]);
for(int i =1 ;i <= m; i++){
for(int j = 1; j <= n; j++){
if(i == 1)
d[i][j] = wh[i][j];
else{
int M = INF;
int l = 1;
if(M > d[i-1][j-1] && j-1 >= 1){
M = d[i-1][j-1];
l = j-1;
}
if(M >= d[i-1][j]){
M = d[i-1][j];
l = j;
}
if(M >= d[i-1][j+1] && j+1 <= n){
M = d[i-1][j+1];
l = j+1;
}
f[i][j] = l;
d[i][j] = M + wh[i][j];
}
}
}
int M = INF;
int l = 1;
for(int i = 1; i <= n; i++){
if(M >= d[m][i]){
M = d[m][i];
l = i;
}
}
printf("Case %d\n",++kase);
dfs(m,l);
printf("%d\n",l);
}
return 0;
}