题目:传送门
思路:求最少时间前提下最大分数,就是在时间相同的时候取积分最大的。在求最短路的时候,加一个maxw记录最大积分,只有当最短路更新时或者最短路相同积分较大时更新最大积分。
下面是代码:
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#include<vector>
#include<algorithm>
#define N 505
#define INF 0x3f3f3f3f
using namespace std;
struct Edge{
int to,tim;
Edge(){};
Edge(int to,int tim)
{
this->to=to;
this->tim=tim;
}
};
struct Pair{
int current,tim;
Pair(){};
Pair(int current,int tim)
{
this->current=current;
this->tim=tim;
}
friend bool operator< (Pair a,Pair b)
{
return a.tim>b.tim;
}
};
int n,m;
vector<Edge> edge[N];
int w[N];
int tim[N],maxw[N];
void addEdge(int from,int to,int w)
{
edge[to].push_back(Edge(from,w));
edge[from].push_back(Edge(to,w));
}
void dijkstra(int s)
{
priority_queue<Pair> q;
fill(tim,tim+n,INF);
fill(maxw,maxw+n,0);
tim[s]=0;
q.push(Pair(s,0));
while(!q.empty())
{
Pair tmp=q.top();
q.pop();
if(tim[tmp.current]<tmp.tim) continue;
for(int i=0;i<edge[tmp.current].size();i++)
{
Edge e=edge[tmp.current][i];
if(tim[e.to]>tim[tmp.current]+e.tim)
{
tim[e.to]=tim[tmp.current]+e.tim;
maxw[e.to]=maxw[tmp.current]+w[e.to];
q.push(Pair(e.to,tim[e.to]));
}
else if(tim[e.to]==tim[tmp.current]+e.tim)
{
maxw[e.to]=max(maxw[e.to],maxw[tmp.current]+w[e.to]);
}
}
}
}
void init()
{
for(int i=0;i<n;i++)
edge[i].clear();
}
int main()
{
int s,t;
while(~scanf("%d%d%d%d",&n,&m,&s,&t))
{
init();
for(int i=0;i<n;i++)
scanf("%d",&w[i]);
int a,b,c;
while(m--)
{
scanf("%d%d%d",&a,&b,&c);
addEdge(a,b,c);
}
dijkstra(s);
printf("%d %d\n",tim[t],maxw[t]+w[s]);
}
}