标签:uva116 unidirectional tsp dp 路径打印
题意:找最短路,知道三种行走方式,给出图,求出一条从左边到右边的最短路,且字典序最小。
思路:用dp记忆化搜索的思想来考虑是思路很清晰的,状态方程:max{ dp[i+1,j+1], dp[i,j+1], dp[i-1,j+1]},
但是困难在如何求出字典序最小的路。
因为左边到右边的字典序最小就必须从左边开始找,于是我们可以换个思路,dp时从右边走到左边,这样寻找路径就可以从左向右了。
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<string>
#include<algorithm>
#include<cstdlib>
#include<set>
#include<queue>
#include<stack>
#include<vector>
#include<map>
#define N 100010
#define Mod 10000007
#define lson l,mid,idx<<1
#define rson mid+1,r,idx<<1|1
#define lc idx<<1
#define rc idx<<1|1
const double EPS = 1e-11;
const double PI = acos(-1.0);
const double E=2.718281828;
typedef long long ll;
const int INF=2147483647;
using namespace std;
int a[11][110];
int d[12][120],next[120][110];
int main()
{
//freopen("in.txt","r",stdin);
int n,m;
while(cin>>m>>n)
{
for(int i=0; i<m; i++)
for(int j=0; j<n; j++)
scanf("%d",&a[i][j]);
int ans=INF,first=0;
//cout<<ans<<endl;
for(int j=n-1; j>=0; j--)
{
for(int i=0; i<m; i++)
{
if(j==n-1)
d[i][j]=a[i][j];
else
{
int row[3]= {i,i-1,i+1};
if(i==0)
row[1]=m-1;
if(i==m-1)
row[2]=0;
sort(row,row+3);
d[i][j]=INF;
for(int k=0; k<3; k++)
{
int v=d[row[k]][j+1]+a[i][j];
if(v<d[i][j])
d[i][j]=v,next[i][j]=row[k];
}
}
if(j==0&&d[i][j]<ans)
ans=d[i][j],first=i;
}
}
printf("%d",first+1);
for(int i=next[first][0],j=1; j<n; i=next[i][j],j++)
printf(" %d",i+1);
printf("\n%d\n",ans);
}
return 0;
}
UVa 116 - Unidirectional TSP(dp)
标签:uva116 unidirectional tsp dp 路径打印
原文地址:http://blog.csdn.net/acm_baihuzi/article/details/40402539