POJ2387(Til the Cows Come Home)

这题就是裸的最短路,而且边权都为非负,可以直接用dijkstra来求。

写这题主要是为了练习一下dijkstra的优先级队列实现,提交后运行时间为63MS,比一般的dijkstra快一点(97MS)。

后来又尝试用SPFA写,结果还是63MS。

在写dijkstra的优先级队列实现和SPFA的过程中发现,这两个算法非常类似,不过,SPFA用的是一般的队列。

SPFA
#include <stdio.h>
#include <string.h>
#include <queue>
using namespace std;
#define MIN(a,b) ((a)<(b)?(a):(b))
#define N 1000
#define INF 100000
int n,m;
int d[N][N],dist[N],inq[N];
struct node
{
    int u;
    friend bool operator <(node x,node y)
    {
        return dist[x.u]>dist[y.u];
    }
};
void spfa(int s)
{
    int u,v;
    node cur,next;
    queue<node> q;
    memset(inq,0,sizeof(inq));
    for(u=0;u<n;u++)    dist[u]=INF;
    dist[s]=0;
    cur.u=s;
    q.push(cur);
    inq[s]=1;
    while(!q.empty())
    {
        cur=q.front(),q.pop();
        u=cur.u;
        inq[u]=0;
        for(v=0;v<n;v++)
        {
            if(dist[v]>dist[u]+d[u][v])
            {
                dist[v]=dist[u]+d[u][v];
                next.u=v;
                if(inq[v]==0)   q.push(next);
            }
        }
    }
}
int main()
{
    int i,j,a,b,x;
    while(~scanf("%d%d",&m,&n))
    {
        for(i=0;i<n;i++)
        {
            for(j=0;j<i;j++)    d[i][j]=d[j][i]=INF;
        }
        for(i=0;i<m;i++)
        {
            scanf("%d%d%d",&a,&b,&x);
            a--,b--;
            d[a][b]=d[b][a]=MIN(d[a][b],x);
        }
        spfa(0);
        printf("%d\n",dist[n-1]);
    }
    return 0;
}
优先级队列实现的dijkstra
#include <stdio.h>
#include <string.h>
#include <queue>
#define MIN(a,b) ((a)<(b)?(a):(b))
#define N 1000
#define INF 100000
using namespace std;
int n,m;
int d[N][N];
int dist[N],vis[N];
struct node
{
    int u,g;
    friend bool operator <(node x,node y)
    {
        return x.g>y.g;
    }
};
void dijkstra(int s)
{
    int u,v,gu,gv;
    node cur,next;
    priority_queue<node> pq;
    memset(vis,0,sizeof(vis));
    for(u=0;u<n;u++)    dist[u]=INF;
    cur.u=s;
    cur.g=0;
    pq.push(cur);
    while(!pq.empty())
    {
        cur=pq.top(),pq.pop();
        u=cur.u;
        gu=cur.g;
        vis[u]++;
        if(vis[u]>1)    continue;
        dist[u]=gu;
        for(v=0;v<n;v++)
        {
            if(vis[v]==0 && dist[v]>=gu+d[u][v])
            {
                dist[v]=gv=gu+d[u][v];
                next.u=v;
                next.g=gv;
                pq.push(next);
            }
        }
    }
}
int main()
{
    int i,j,a,b,x;
    while(~scanf("%d%d",&m,&n))
    {
        for(i=0;i<n;i++)
        {
            for(j=0;j<i;j++)    d[i][j]=d[j][i]=INF;
        }
        for(i=0;i<m;i++)
        {
            scanf("%d%d%d",&a,&b,&x);
            a--,b--;
            d[a][b]=d[b][a]=MIN(d[a][b],x);
        }
        dijkstra(0);
        printf("%d\n",dist[n-1]);
    }
    return 0;
}
posted @ 2012-07-09 14:59  BeatLJ  阅读(213)  评论(0编辑  收藏  举报