思路 :很基础的题目,如果把费用去掉就是妥妥的dijkstra模板题,现在多了一个条件,但还是求最短路,只是在可以保证最短路的情况下,费用尽量小,很好理解,但是要细心。
这种题居然也能WA两次。。
下面是AC代码 :
#include<iostream>
#include<cstring>
#include<queue>
#include<cstdio>
using namespace std;
const int maxn = 1e5 + 5;
const int INF = 0x3f3f3f3f;
struct node
{
int v, w, val, next;
}e[maxn];
struct edge
{
int id, w, val;
operator < (const edge &oth) const
{
return w > oth.w;
}
}mid;
int head[maxn], n, m, cnt;
int dis[maxn], val[maxn];
priority_queue <edge> q;
void init() {
memset(dis, INF, sizeof(dis));
memset(val, INF, sizeof(val));
memset(head, -1, sizeof(head));
memset(e, 0, sizeof(e));
cnt = 0;
}
void add (int from, int to, int dis, int pi) {
e[++cnt].v = to;
e[cnt].w = dis;
e[cnt].val = pi;
e[cnt].next = head[from];
head[from] = cnt;
}
void dijktra(int u) {
dis[u] = 0;
val[u] = 0;
q.push({u, 0, 0});
while (!q.empty()) {
mid = q.top();
q.pop();
int ans = mid.id;
if (mid.w != dis[ans]) continue;
for (int i = head[ans]; i != -1; i = e[i].next) {
if (dis[e[i].v] > dis[ans] + e[i].w) {
dis[e[i].v] = dis[ans] + e[i].w;
val[e[i].v] = val[ans] + e[i].val;
q.push({e[i].v, dis[e[i].v], val[e[i].val]});
}
else if (dis[e[i].v] == dis[ans] + e[i].w && val[e[i].v] > val[ans] + e[i].val) {
val[e[i].v] = val[ans] + e[i].val;
dis[e[i].v] = dis[ans] + e[i].w;
q.push({e[i].v, dis[e[i].v], val[e[i].val]});
}
}
}
}
int main()
{
while (scanf("%d%d", &n, &m) && n + m) {
init();
for (int i = 0; i < m; i++) {
int ui, vi, wi, pi;
scanf("%d%d%d%d", &ui, &vi, &wi, &pi);
add (ui, vi, wi, pi);
add (vi, ui, wi, pi);
}
int ai, bi;
scanf("%d%d", &ai, &bi);
dijktra(ai);
cout << dis[bi] << " " << val[bi] << endl;
}
return 0;
}