http://poj.org/problem?id=2457
题意:求起点1到终点m的最短距离。这个可以spfa||dijkstra。这题关键的是要输出从1--m走过的路径。用path[]记录下,每一步的祖先,用shortest[]逆序输出即可。这题re了n次。到现在也不理解,为什么先
if(dis[m]==INF){//为什么先判断就不会re.不明白
printf("-1\n");
continue;
}
这个就没问题。
![](https://i-blog.csdnimg.cn/blog_migrate/cdec0645add3fc3c328197dda5c76203.gif)
// I'm lanjiangzhou //C #include <stdio.h> #include <stdlib.h> #include <string.h> #include <ctype.h> #include <math.h> #include <time.h> //C++ #include <iostream> #include <algorithm> #include <cstdio> #include <cstdlib> #include <cmath> #include <cstring> #include <cctype> #include <stack> #include <string> #include <list> #include <queue> #include <map> #include <vector> #include <deque> #include <set> using namespace std; //*************************OUTPUT************************* #ifdef WIN32 #define INT64 "%I64d" #define UINT64 "%I64u" #else #define INT64 "%lld" #define UINT64 "%llu" #endif //**************************CONSTANT*********************** #define INF 0x3f3f3f3f #define eps 1e-8 #define PI acos(-1.) #define PI2 asin (1.); typedef long long LL; //typedef __int64 LL; //codeforces typedef unsigned int ui; typedef unsigned long long ui64; #define MP make_pair typedef vector<int> VI; typedef pair<int, int> PII; #define pb push_back #define mp make_pair //***************************SENTENCE************************ #define CL(a,b) memset (a, b, sizeof (a)) #define sqr(a,b) sqrt ((double)(a)*(a) + (double)(b)*(b)) #define sqr3(a,b,c) sqrt((double)(a)*(a) + (double)(b)*(b) + (double)(c)*(c)) //****************************FUNCTION************************ template <typename T> double DIS(T va, T vb) { return sqr(va.x - vb.x, va.y - vb.y); } template <class T> inline T INTEGER_LEN(T v) { int len = 1; while (v /= 10) ++len; return len; } template <typename T> inline T square(T va, T vb) { return va * va + vb * vb; } // aply for the memory of the stack //#pragma comment (linker, "/STACK:1024000000,1024000000") //end #define maxn 2100 int n,m; int edges[maxn][maxn]; int S[maxn]; int dis[maxn]; int path[maxn]; int shortest[maxn]; void dijkstra(int v0){ for(int i=1;i<=m;i++){ dis[i]=edges[v0][i]; S[i]=0; if(i!=v0&&dis[i]<INF) path[i]=v0; else path[i]=-1; } S[v0]=1; dis[v0]=0; for(int i=1;i<=m-1;i++){ int min=INF,u=v0; for(int j=1;j<=m;j++){ if(!S[j]&&dis[j]<min){ u=j; min=dis[j]; } } S[u]=1; for(int k=1;k<=m;k++){ if(!S[k]&&edges[u][k]<INF&&dis[u]+edges[u][k]<dis[k]){ dis[k]=dis[u]+edges[u][k]; path[k]=u; } } } } int main(){ while(scanf("%d%d",&n,&m)!=EOF){ int u,v; //³õʼ»¯ for(int i=1;i<=m;i++){ for(int j=1;j<=m;j++){ edges[i][j]=INF; } edges[i][i]=0; } for(int i=1;i<=n;i++){ scanf("%d%d",&u,&v); edges[u][v]=1; } dijkstra(1); if(dis[m]==INF){//为什么先判断就不会re.不明白 printf("-1\n"); continue; } //printf("dis[m]=%d\n",dis[m]); memset(shortest,0,sizeof(shortest)); int k=0; shortest[k]=m; while(path[shortest[k]]!=1){ k++; shortest[k]=path[shortest[k-1]]; } k++; shortest[k]=1; // if(dis[m]==INF){//为什么把dis[m]==INF放在这里就不会re.擦,re了13次。 // printf("-1\n"); // } // else { printf("%d\n",dis[m]+1); for(int j=k;j>0;j--){ printf("%d\n",shortest[j]); } printf("%d\n",shortest[0]); //} } return 0; }