您的位置:首页 > 其它

最短路径之 Dijkstra模板

2015-02-10 22:42 302 查看
一:时间复杂度为O(V*V)的Dijkstra

const int Max_v = 100 + 10;
const int INF = 1<<30;
int cost[Max_v][Max_v];//权值
int d[Max_v];//顶点s出发最短距离
bool used[Max_v];//以使用过的图
int V;//顶点数
int Edge;//边数

void dijkstra(int s)
{

    fill(d,d+V,INF);
    fill(used,used+V,false);
    d[s]  = 0;
    while(true)
    {
        int v = -1;
        for(int u = 0; u<V; u++)
        {
            if(!used[u] && (v == -1 || d[u] < d[v]))  v = u;
        }
        if(v == -1) break;
        used[v] = true;
        for(int u = 0; u <V; u++)
        {
            d[u] = min(d[u],d[v] + cost[v][u]);
        }
    }
  printf("%d\n",d[V-1]);
}


二:时间复杂度为O(E*logV)的Dijkstra(优先级队列优化后的)

const int maxn = 1000 + 10;
const int INF = 1<<30;
typedef pair<int, int> P;
int N, R;
struct edge
{
    int to, cost;
};
vector<edge> G[maxn];
int d[maxn];  //最短路径

void solve()
{
    priority_queue<P, vector<P>, greater<P> > que;
    fill(d, d+N, INF);  //最短距离

    d[0] = 0;
    que.push(P(0,0));
    while(!que.empty())
    {
        P p = que.top();
        que.pop();
        int v = p.second;
        if(d[v] < p.first) continue;
        for(int i=0; i<G[v].size(); ++i)
        {
            edge e = G[v][i];
            if(d[e.to] > d[v] + e.cost)
            {
                d[e.to] = d[v] + e.cost;
                que.push(P(d[e.to],e.to));
            }

        }
    }
    printf("%d\n",d[N-1]);
}


三:模板题目HDU2544

Description

在每年的校赛里,所有进入决赛的同学都会获得一件很漂亮的t-shirt。但是每当我们的工作人员把上百件的衣服从商店运回到赛场的时候,却是非常累的!所以现在他们想要寻找最短的从商店到赛场的路线,你可以帮助他们吗?



Input

输入包括多组数据。每组数据第一行是两个整数N、M(N<=100,M<=10000),N表示成都的大街上有几个路口,标号为1的路口是商店所在地,标号为N的路口是赛场所在地,M则表示在成都有几条路。N=M=0表示输入结束。接下来M行,每行包括3个整数A,B,C(1<=A,B<=N,1<=C<=1000),表示在路口A与路口B之间有一条路,我们的工作人员需要C分钟的时间走过这条路。

输入保证至少存在1条商店到赛场的路线。



Output

对于每组输入,输出一行,表示工作人员从商店走到赛场的最短时间


Sample Input

2 1
1 2 3
3 3
1 2 5
2 3 5
3 1 2
0 0




Sample Output

3
2




第一种AC代码

#include <iostream>
#include <cstdio>
#include <cstring>
#include <vector>
#include <queue>
#include <algorithm>
using namespace std;

const int Max_v = 100 + 10; const int INF = 1<<30; int cost[Max_v][Max_v];//权值 int d[Max_v];//顶点s出发最短距离 bool used[Max_v];//以使用过的图 int V;//顶点数 int Edge;//边数 void dijkstra(int s) { fill(d,d+V,INF); fill(used,used+V,false); d[s] = 0; while(true) { int v = -1; for(int u = 0; u<V; u++) { if(!used[u] && (v == -1 || d[u] < d[v])) v = u; } if(v == -1) break; used[v] = true; for(int u = 0; u <V; u++) { d[u] = min(d[u],d[v] + cost[v][u]); } } printf("%d\n",d[V-1]); }
int main()
{
#ifdef xxz
freopen("in.txt","r",stdin);
#endif // xxz
int Case;
while(scanf("%d%d",&V,&Edge) != EOF)
{
if(V == 0 && Edge == 0) break;
for(int i = 0; i < Max_v; i++) fill(cost[i],cost[i]+Max_v,INF);//注意每次都要初始化权值,否则WA
for(int i = 0 ; i < Edge; i++)
{
int u,v,value;
scanf("%d%d%d",&u,&v,&value);
u--,v--;
cost[u][v] = cost[v][u] = value;
}
dijkstra(0);
}
return 0;
}


第二种AC代码(堆优化)

#include <cstdio>
#include <cstring>
#include <vector>
#include <queue>
#include <algorithm>
using namespace std;

const int maxn = 1000 + 10; const int INF = 1<<30; typedef pair<int, int> P; int N, R; struct edge { int to, cost; }; vector<edge> G[maxn]; int d[maxn]; //最短路径 void solve() { priority_queue<P, vector<P>, greater<P> > que; fill(d, d+N, INF); //最短距离 d[0] = 0; que.push(P(0,0)); while(!que.empty()) { P p = que.top(); que.pop(); int v = p.second; if(d[v] < p.first) continue; for(int i=0; i<G[v].size(); ++i) { edge e = G[v][i]; if(d[e.to] > d[v] + e.cost) { d[e.to] = d[v] + e.cost; que.push(P(d[e.to],e.to)); } } } printf("%d\n",d[N-1]); }

int main()
{
int i, a, b, c;
edge e;
while(~scanf("%d%d",&N,&R))
{
if(N == 0 && R == 0) break;
for(i = 0; i < maxn; i++) G[i].clear();

for(i=0; i<R; ++i)
{
scanf("%d%d%d", &a, &b, &c);
a--,b--;
e.to = b, e.cost = c;
G[a].push_back(e);
e.to = a;
G[b].push_back(e);
}
solve();
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: