PTA 7-3 旅游规划 (25分)(双权值Dijkstra最短路)

7-3 旅游规划 (25分)

有了一张自驾旅游路线图,你会知道城市间的高速公路长度、以及该公路要收取的过路费。现在需要你写一个程序,帮助前来咨询的游客找一条出发地和目的地之间的最短路径。如果有若干条路径都是最短的,那么需要输出最便宜的一条路径。

输入格式:

输入说明:输入数据的第1行给出4个正整数N、M、S、D,其中N(2≤N≤500)是城市的个数,顺便假设城市的编号为0~(N−1);M是高速公路的条数;S是出发地的城市编号;D是目的地的城市编号。随后的M行中,每行给出一条高速公路的信息,分别是:城市1、城市2、高速公路长度、收费额,中间用空格分开,数字均为整数且不超过500。输入保证解的存在。

输出格式:

在一行里输出路径的长度和收费总额,数字间以空格分隔,输出结尾不能有多余空格。

p t a pta pta良心题

D i j k s t r a Dijkstra Dijkstra模板题,只不过是双权值多了一个判定就好,还是比较简单的。
不过注意链式前向星没办法处理重边的问题,所以最好用

#include
#include
#include
#include
#include
#include
#include

#define over(i,s,t) for(register int i = s;i <= t;++i)
#define lver(i,t,s) for(register int i = t;i >= s;--i)
//#define int __int128
#define lowbit(p) p&(-p)
using namespace std;

typedef long long ll;
typedef pair<int,int> PII;
const int N = 4e5+7;

struct Node{
    int id,w,val;
    bool operator<(const Node &t)const {
        if(w == t.w)
            return val > t.val;
        return w > t.w;
    }
};
int n,m,s,t;
struct node{
    int v,w,val,nex;
}e[N];
int head[N],tot;

inline void add(int u,int v,int w,int val){
    e[++tot].v = v;
    e[tot].nex = head[u];
    e[tot].val = val;
    e[tot].w = w;
    head[u] = tot;
}
int dis[N],value[N];
int vis[N];
priority_queue<Node>q;
void Dijkstra(int x){
    memset(dis,0x3f,sizeof dis);
    memset(value,0x3f,sizeof value);
    dis[x] = value[x] = 0;
    q.push({x,0,0});
    while(q.size()){
        int u = q.top().id;
        q.pop();
        if(vis[u])continue;
        vis[u] = 1;
        for(int i = head[u];~i;i = e[i].nex){
            int v =e[i].v,now_w = e[i].w,now_val = e[i].val;
            if(dis[v] > dis[u] + now_w){
                dis[v] = dis[u] + now_w;
                value[v] = value[u] + now_val;
                q.push({v,dis[v],value[v]});
            }
            else if(dis[v] == dis[u] + now_w && value[v] > value[u] + now_val){
                value[v] = value[u] + now_val;
                q.push({v,dis[v],value[v]});
            }
        }
    }
}

int main()
{
    cin>>n>>m>>s>>t;
    memset(head,-1,sizeof head);
    over(i,1,m){
        int u,v,w,val;
        scanf("%d%d%d%d",&u,&v,&w,&val);
        add(u,v,w,val);
        add(v,u,w,val);
    }
    Dijkstra(s);
    printf("%d %d",dis[t],value[t]);
    return 0;
}

你可能感兴趣的:(#,最短路算法)