POJ 2387 dijkstra 和 SPFA
已知很多边及路径长度,求从起点到终点的最短路径长度。
最短路问题:
1.Dijkstra算法,试用于有向图和无向图,正权图,同时方便打印路径。思路:每次扩展一个距离最短的点,更新与其相邻的点的距离。
2.SPFA算法:即使用优先对列的Dijkstra算法。注意用数组vis[]标记该点到该点的最短距离是否已求出。
3.Bellman-Ford算法 边上带有负值的单源最短路
Dijkstra:(一个陷阱:保存两点之间的路径时要保存最小的)
#include<cstdio>
#include<cstring>
#include<iostream>
using namespace std;
#define INF 10000000
int w[2010][2010],d[2010],n,t;
bool vis[2010];
void dijkstra()
{
for(int i=1; i<=n; i++)
{
int x,m=INF;
for(int y=1; y<=n; y++)
if(!vis[y]&&d[y]<=m)
m=d[x=y];
vis[x]=1;
for(int y=1; y<=n; y++)
d[y]=min(d[y],d[x]+w[x][y]);
}
}
void init()
{
for(int i=0; i<=n; i++)
{
vis[i]=false;
d[i]=INF;
for(int j=0; j<=n; j++)
w[i][j]=INF;
}
d[n]=0;
}
int main()
{
// freopen("in.txt","r",stdin);
scanf("%d%d",&t,&n);
init();
for(int i=0; i<t; i++)
{
int a,b,c;
scanf("%d%d%d",&a,&b,&c);
if(c<w[a][b])
w[a][b]=c,w[b][a]=c;
}
dijkstra();
printf("%d\n",d[1]);
return 0;
}
SPFA:
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cstdlib>
#include<cmath>
#include<iostream>
#include<vector>
#include<queue>
#define MAXN 1000001+10
#define ULL unsigned long long
#define LL long long
#define INF 1000000000
using namespace std;
typedef struct node
{
int aim,dis;
node (int a=0,int b=0)
{
aim=a;
dis=b;
}
bool operator <(const node & th) const
{
return th.dis<dis;
}
} node;
vector<int>G[2010];
vector<int>w[2010];
int d[2010];
bool vis[2010];
int main()
{
// freopen("in.txt","r",stdin);
int n,t;
while(scanf("%d%d",&n,&t)!=EOF)
{
memset(vis,false,sizeof(vis));
for(int i=0; i<=n; i++)
{
G[i].clear();
w[i].clear();
d[i]=INF;
}
for(int i=0; i<t; i++)
{
int a,b,c;
scanf("%d%d%d",&a,&b,&c);
G[a].push_back(b);
w[a].push_back(c);
w[b].push_back(c);
G[b].push_back(a);
}
d[n]=0;
priority_queue<node>q;
node aa(n,0);
q.push(aa);
while(!q.empty())
{
node v=q.top();
q.pop();
int u=v.aim;
if(vis[u]) continue;
vis[u]=true;
for(int i=0; i<(int)G[u].size(); i++)
{
int a=G[u][i];
if(d[a]>w[u][i]+d[u])
{
d[a]=w[u][i]+d[u];
node aa(a,d[a]);
q.push(aa);
}
}
}
printf("%d\n",d[1]);
}
return 0;
}

浙公网安备 33010602011771号