http://acm.hdu.edu.cn/showproblem.php?pid=1874
题目大意:
给你一些点,让你求S到T的最短路径。
我只是来练习一下SPFA的
dijkstra+邻接矩阵
- #include<cstdio>
- #include<cstring>
- const int MAXN=200+10;
- const int INF=1000000;
- int n,m,map[MAXN][MAXN],dis[MAXN];
- bool vis[MAXN];
- void dijkstra(int s)
- {
- memset(vis,0,sizeof(vis));
- int cur=s;
- dis[cur]=0;
- vis[cur]=1;
- for(int i=0;i<n;i++)
- {
- for(int j=0;j<n;j++)
- if(!vis[j] && dis[cur] + map[cur][j] < dis[j])
- dis[j]=dis[cur] + map[cur][j] ;
- int mini=INF;
- for(int j=0;j<n;j++)
- if(!vis[j] && dis[j] < mini)
- mini=dis[cur=j];
- vis[cur]=true;
- }
- }
- int main()
- {
- while(~scanf("%d%d",&n,&m))
- {
- for(int i=0;i<n;i++)
- {
- dis[i]=INF;
- for(int j=0;j<n;j++)
- map[i][j]=INF;
- }
- for(int i=0;i<m;i++)
- {
- int from,to,val;
- scanf("%d%d%d",&from,&to,&val);
- if(map[from][to] > val)
- map[to][from]=map[from][to]=val;
- }
- int s,t;
- scanf("%d%d",&s,&t);
- dijkstra(s);
- if(dis[t]==INF)
- printf("-1\n");
- else
- printf("%d\n",dis[t]);
- }
- return 0;
- }
dijkstra+优先队列
- #include<cstdio>
- #include<cstring>
- #include<queue>
- using namespace std;
- const int MAXN=200+10;
- const int MAXM=40000+10;
- const int INF=1000000;
- int n,m,dis[MAXN],head[MAXN],len;
- bool vis[MAXN];
- struct edge
- {
- int to,val,next;
- }e[MAXM];
- void add(int from,int to,int val)
- {
- e[len].to=to;
- e[len].val=val;
- e[len].next=head[from];
- head[from]=len++;
- }
- struct point
- {
- int val,id;
- point(int id,int val):id(id),val(val){}
- bool operator <(const point &x)const{
- return val>x.val;
- }
- };
- void dijkstra(int s)
- {
- memset(vis,0,sizeof(vis));
- for(int i=0;i<n;i++)
- dis[i]=INF;
- priority_queue<point> q;
- q.push(point(s,0));
- dis[s]=0;
- while(!q.empty())
- {
- int cur=q.top().id;
- q.pop();
- if(vis[cur]) continue;
- vis[cur]=true;
- for(int i=head[cur];i!=-1;i=e[i].next)
- {
- int id=e[i].to;
- if(!vis[id] && dis[cur]+e[i].val < dis[id])
- {
- dis[id]=dis[cur]+e[i].val;
- q.push(point(id,dis[id]));
- }
- }
- }
- }
- int main()
- {
- while(~scanf("%d%d",&n,&m))
- {
- len=0;
- memset(head,-1,sizeof(head));
- for(int i=0;i<m;i++)
- {
- int from,to,val;
- scanf("%d%d%d",&from,&to,&val);
- add(from,to,val);
- add(to,from,val);
- }
- int s,t;
- scanf("%d%d",&s,&t);
- dijkstra(s);
- if(dis[t]==INF)
- printf("-1\n");
- else
- printf("%d\n",dis[t]);
- }
- return 0;
- }
SPFA+邻接矩阵:
- #include<cstdio>
- #include<queue>
- using namespace std;
- const int INF=1000000;
- const int MAXN=200+10;
- int n,m;
- int map[MAXN][MAXN];
- int dis[MAXN];
- void SPFA(int s)
- {
- for(int i=0;i<n;i++)
- dis[i]=INF;
- bool vis[MAXN]={0};
- vis[s]=true;
- dis[s]=0;
- queue<int> q;
- q.push(s);
- while(!q.empty())
- {
- int cur=q.front();
- q.pop();
- vis[cur]=false;
- for(int i=0;i<n;i++)
- {
- if(dis[cur] + map[cur][i] < dis[i])
- {
- dis[i]=dis[cur] + map[cur][i];
- if(!vis[i])
- {
- q.push(i);
- vis[i]=true;
- }
- }
- }
- }
- }
- int main()
- {
- while(~scanf("%d%d",&n,&m))
- {
- for(int i=0;i<n;i++)
- for(int j=0;j<n;j++)
- map[i][j]=INF;
- for(int i=0;i<m;i++)
- {
- int from,to,dis;
- scanf("%d%d%d",&from,&to,&dis);
- if(map[from][to]>dis)
- map[from][to]=map[to][from]=dis;
- }
- int s,t;
- scanf("%d%d",&s,&t);
- SPFA(s);
- if(dis[t]==INF)
- puts("-1");
- else
- printf("%d\n",dis[t]);
- }
- return 0;
- }
SPFA+邻接表
- #include<cstdio>
- #include<cstring>
- #include<queue>
- using namespace std;
- const int MAXN=200+10;
- const int MAXM=40000+10;
- const int INF=1000000;
- int n,m,dis[MAXN],head[MAXN],len;
- bool vis[MAXN];
- struct edge
- {
- int to,val,next;
- }e[MAXM];
- void add(int from,int to,int val)
- {
- e[len].to=to;
- e[len].val=val;
- e[len].next=head[from];
- head[from]=len++;
- }
- void spfa(int s)
- {
- memset(vis,0,sizeof(vis));
- for(int i=0;i<n;i++)
- dis[i]=INF;
- queue<int> q;
- q.push(s);
- vis[s]=true;
- dis[s]=0;
- while(!q.empty())
- {
- int cur=q.front();
- q.pop();
- vis[cur]=false;
- for(int i=head[cur];i!=-1;i=e[i].next)
- {
- int id=e[i].to;
- if(dis[id] > dis[cur]+e[i].val)
- {
- dis[id] = dis[cur] + e[i].val;
- if(!vis[id])
- {
- vis[id]=true;
- q.push(id);
- }
- }
- }
- }
- }
- int main()
- {
- while(~scanf("%d%d",&n,&m))
- {
- len=0;
- memset(head,-1,sizeof(head));
- for(int i=0;i<m;i++)
- {
- int from,to,val;
- scanf("%d%d%d",&from,&to,&val);
- add(from,to,val);
- add(to,from,val);
- }
- int s,t;
- scanf("%d%d",&s,&t);
- spfa(s);
- if(dis[t]==INF)
- printf("-1\n");
- else
- printf("%d\n",dis[t]);
- }
- return 0;
- }
floyd:
- #include<cstdio>
- #include<cstring>
- #include<algorithm>
- using namespace std;
- const int MAXN=200+10;
- const int INF=1000000;
- int n,m,dis[MAXN][MAXN];
- void floyd()
- {
- for(int k=0;k<n;k++)
- for(int i=0;i<n;i++)
- for(int j=0;j<n;j++)
- dis[i][j]=min(dis[i][j],dis[i][k]+dis[k][j]);
- }
- int main()
- {
- while(~scanf("%d%d",&n,&m))
- {
- for(int i=0;i<n;i++)
- for(int j=0;j<n;j++)
- dis[i][j]=INF;
- for(int i=0;i<m;i++)
- {
- int from,to,val;
- scanf("%d%d%d",&from,&to,&val);
- if(dis[from][to] > val)
- dis[to][from]=dis[from][to]=val;
- }
- int s,t;
- scanf("%d%d",&s,&t);
- if(s==t)
- {
- printf("0\n");
- continue;
- }
- floyd();
- if(dis[s][t]==INF)
- printf("-1\n");
- else
- printf("%d\n",dis[s][t]);
- }
- return 0;
- }