kuangbin(dijstra算法模板)

版权声明:本文为博主原创文章,转载请说明出处。 https://blog.csdn.net/xianpingping/article/details/82927371

1.vector

不要忘记vector初始化!

代码:

#include<bits/stdc++.h>
using namespace std;
#define ll long long
const int mod=1e9+7;
const int INF=0x3f3f3f3f;
const int MAXN=2000010;

struct qnode
{
    int v;
    int c;
    qnode(int _v=0,int _c=0):v(_v),c(_c) {}
    bool operator <(const qnode &r)const
    {
        return c>r.c;
    }
};
struct Edge
{
    int v,cost;
    Edge(int _v=0,int _cost=0):v(_v),cost(_cost) {}
};
vector<Edge>E[MAXN];
bool vis[MAXN];
int dist[MAXN];
//点的编号从 1 开始
void Dijkstra(int n,int start)
{
    memset(vis,false,sizeof(vis));
    for(int i=1; i<=n; i++)dist[i]=INF;
    priority_queue<qnode>que;
    while(!que.empty())que.pop();
    dist[start]=0;
    que.push(qnode(start,0));
    qnode tmp;
    while(!que.empty())
    {
        tmp=que.top();
        que.pop();
        int u=tmp.v;
        if(vis[u])continue;
        vis[u]=true;
        for(int i=0; i<E[u].size(); i++)
        {
            int v=E[tmp.v][i].v;
            int cost=E[u][i].cost;
            if(!vis[v]&&dist[v]>dist[u]+cost)
            {
                dist[v]=dist[u]+cost;
                que.push(qnode(v,dist[v]));
            }
        }
    }
}
void add(int u,int v,int w)
{
    E[u].push_back(Edge(v,w));
}
int a[MAXN],c[MAXN];
int shuchu[MAXN];
int main()
{
    int cas=0;
    int t,tt,n,m,s,x;
    scanf("%d",&tt);
    while(tt--){
        cas++;
        scanf("%d%d",&n,&m);
        for(int i=1;i<=n+m;i++)
            E[i].clear();///这个地方要记住,不要忘记初始化!!
        for(int i=1;i<=m;i++)
        {
            scanf("%d%d",&t,&s);
            for(int j=1;j<=s;j++){
                scanf("%d",&x);
                add(x,i+n,t);
                add(i+n,x,0);
            }
        }
        Dijkstra(n+m,1);
        for(int i=1;i<=n;i++){
            a[i]=dist[i];
        }
        Dijkstra(n+m,n);
        for(int i=1;i<=n;i++){
            c[i]=max(a[i],dist[i]);
        }
        ll minn=INF;
        for(int i=1;i<=n;i++){
            if(minn>c[i])
            minn=c[i];
        }
        int cnt=0;
        printf("Case #%d: ",cas);
        if(minn==INF){
            printf("Evil John\n");
            continue;
        }
        else{
        printf("%d\n",minn);
        for(int i=1;i<=n;i++){
            if(c[i]==minn)
            {shuchu[++cnt]=i;}
        }
        for(int i=1;i<cnt;i++){
            printf("%d ",shuchu[i]);
        }
        printf("%d\n",shuchu[cnt]);
    }
    }
    return 0;
}
/*
2
5 4
1 3 1 2 3
2 2 3 4
10 2 1 5
3 3 3 4 5
3 1
1 2 1 2
*/

2.邻接表:

相比较vector要快一点。但是要简便的时候tol会很大。不要忘记初始化init()

代码:

#include <iostream>
#include <string.h>
#include <stdio.h>
#include <algorithm>
#include <queue>
#include <vector>
using namespace std;
/*
 * 使用优先队列优化Dijkstra算法
 * 复杂度O(ElogE)
 * 注意对vector<Edge>E[MAXN]进行初始化后加边
 */
const int INF=1e18;
const int maxm=5300100;
const int maxn=200000+100;
typedef long long LL;
struct qnode
{
    int v;
    int c;
    qnode(int _v=0,int _c=0):v(_v),c(_c){}
    bool operator <(const qnode &r)const
    {
        return c>r.c;
    }
};
struct Edge
{
    int v,cost;
    int next;
};
Edge edge[maxm];
int tol;
int head[maxm];
bool vis[maxn];
LL dist[maxn];
void Dijkstra(int n,int start)//点的编号从1开始
{
    memset(vis,false,sizeof(vis));
    for(int i=1;i<=n;i++)dist[i]=INF;
    priority_queue<qnode>que;
    while(!que.empty())que.pop();
    dist[start]=0;
    que.push(qnode(start,0));
    qnode tmp;
    while(!que.empty())
    {
        tmp=que.top();
        que.pop();
        int u=tmp.v;
        if(vis[u])continue;
        vis[u]=true;
        for(int i=head[u];i!=-1;i=edge[i].next)
        {
            int v=edge[i].v;
            int cost=edge[i].cost;
            if(!vis[v]&&dist[v]>dist[u]+cost)
            {
                dist[v]=dist[u]+cost;
                que.push(qnode(v,dist[v]));
            }
        }
    }
}
void add(int u,int v,int w)
{
    edge[tol].v=v;
    edge[tol].cost=w;
    edge[tol].next=head[u];
    head[u]=tol++;
}
void init(){
    memset(head,-1,sizeof(head));
    tol=0;
}
LL a[maxn],c[maxn];
LL shuchu[maxn];
int main()
{
    int cas=0;
    int t,tt,n,m,s,x;
    scanf("%d",&tt);
    while(tt--){
        init();
        cas++;
        scanf("%d%d",&n,&m);
        ///for(int i=1;i<=n+m;i++)E[i].clear();
        for(int i=1;i<=m;i++)
        {
            scanf("%d%d",&t,&s);
            for(int j=1;j<=s;j++){
                scanf("%d",&x);
                add(x,i+n,t);
                add(i+n,x,0);
            }
        }
        Dijkstra(n+m,1);
        for(int i=1;i<=n;i++){
            a[i]=dist[i];
        }
        Dijkstra(n+m,n);
        for(int i=1;i<=n;i++){
            c[i]=max(a[i],dist[i]);
        }
        LL minn=INF;
        for(int i=1;i<=n;i++){
            if(minn>c[i])
            minn=c[i];
        }
        int cnt=0;
        printf("Case #%d: ",cas);
        if(minn==INF){
            printf("Evil John\n");
            continue;
        }
        else{
        printf("%d\n",minn);
        for(int i=1;i<=n;i++){
            if(c[i]==minn)
            {shuchu[++cnt]=i;}
        }
        for(int i=1;i<cnt;i++){
            printf("%d ",shuchu[i]);
        }
        printf("%d\n",shuchu[cnt]);
    }
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/xianpingping/article/details/82927371
今日推荐