(beginer) 最短路 UVA 10246 Asterix and Obelix

Problem A

Asterix and Obelix

Input: standard input

Output: standard output

Time Limit: 5 seconds

Memory Limit: 32 MB

 

After winning a gruesome battle against the Romans in a far-away land, Asterix and his dearest friend Obelix are now returning home. However Obelix is not with Asterix now. He has left Asterix in order to deliver menhir to one of his international buyers (as you probably know, recently he has extended his trade to international markets). But he has promised to join Asterix on his way home and Asterix has promised to host a feast for Obelix (you know how fat he is!) in the city they meet. Obelix may meet Asterix in any city on his way home including the starting and the destination city.

 

(beginer) 最短路 UVA 10246 Asterix and Obelix - 恶魔仁 - 恶魔仁

 

Now Asterix is sitting with a map and trying to figure out the cheapest route home. The map shows the cities and the cost (in sestertii) of going from one city to another if there is a road connecting them directly. For each city in the map Asterix has also calculated the cost (in sestertii) of hosting a feast for Obelix in that city. There will be only one feast and for safety Asterix has decided to set aside enough sestertii to host a feast in the costliest city on the route.

 

Since Asterix does not have a computer, he seeks your help to find out the cheapest route home.

 

Input

 

The input may contain multiple test cases.

 

The first line of each test case contains three integers C (? 80), R (? 1000) and Q (? 6320) where C indicates the number of cities (cities are numbered using distinct integers ranging from 1 to C), R represents the number of roads and Q is the number of queries.

 

The next line contains C integers where the i-th integer fi is the cost (in sestertii) of hosting a feast in city i.

 

Each of the next R lines contains three integers: c1, c2 (? c1) and d indicating that the cost of going from city c1 to c2 (or from c2 to c1) is d sestertii.

 

Each of the next Q lines contains two integers c1 and c2 (c1 ? c2) asking for the cost (in sestertii) of the cheapest route from city c1 to city c2.

 

The input will terminate with three zeros form C, S and Q.

 

Output

 

For each test case in the input first output the test case number (starting from 1) as shown in the sample output. Then for each query in the input print a line giving the minimum cost (in sestertii) of going from the first to the second city in the query. If there exists no path between them just print “–1”.

 

Print a blank line between two consecutive test cases.

 

Sample Input

 

7 8 5

2 3 5 15 4 4 6

1 2 20

1 4 20

1 5 50

2 3 10

3 4 10

3 5 10

4 5 15

6 7 10

1 5

1 6

5 1

3 1

6 7

4 4 2

2 1 8 3

1 2 7

1 3 5

2 4 8

3 4 6

1 4

2 3

0 0 0

 

Sample Output

 

Case #1

45

-1

45

35

16

 

Case #2

18

20



题意:有一个图,给出城市与城市间的路的花费,以及城市举行宴会的花费,然后问从s到t,最小花费为多少,其中花费的计算方法是s到t的路费加上经过的城市中宴会花费最高的花费。

思路:直接dijkstra求出任意两点的答案存在数组里面(复杂度为n*m*log(n)),然后询问的时候直接输出就行了。

代码:
#include<iostream>
#include<cstdio>
#include<vector>
#include<cstring>
#include<queue>
#include<map>
#include<string.h>
using namespace std;
const int maxn = 85;
const int inf = 1e9;
int f[maxn] , d[maxn][maxn];
bool done[maxn][maxn];
int ans[maxn][maxn];
map<int,int> Hash;
int n , m , q , ptr;
struct State
{
State(int uu,int dd,int mm) : u(uu) , dist(dd) , maxcost(mm) { }
int u;
int dist;
int maxcost;
};

inline bool operator < (const State & s1,const State & s2)
{
if (s1.dist==s2.dist) return s1.maxcost > s2.maxcost;
return s1.dist > s2.dist;
}

struct node
{
int v;
int w;
node *next;
} edge[2000+10] , *first[maxn];

void add(int x,int y,int w)
{
edge[++ptr].v = y;
edge[ptr].w = w;
edge[ptr].next = first[x];
first[x] = &edge[ptr];
}

void init()
{
memset(first,0,sizeof(first));
ptr = 0;
}

void input()
{
Hash.clear();
for (int i = 1 ; i <= n ; ++i)
{
scanf("%d",f+i);
Hash[f[i]] = i;
}
int u , v , w;
while (m--)
{
scanf("%d%d%d",&u,&v,&w);
add(u,v,w);
add(v,u,w);
}
}

void Dij(int s)
{
for (int i = 1 ; i <= n ; ++i)
for (int j = 1 ; j <= n ; ++j)
d[i][j] = inf;
memset(done,0,sizeof(done));
priority_queue<State> q;
q.push(State(s,0,Hash[f[s]]));
d[s][Hash[f[s]]] = 0;
int u , v , w , maxcost;
while (q.size())
{
State tmp = q.top(); q.pop();
u = tmp.u , maxcost = tmp.maxcost;
if (done[u][maxcost]) continue;
done[u][maxcost] = true;
for (node * p = first[u] ; p ; p = p->next)
{
v = p->v , w = p->w;
int newcost = Hash[max(f[v],f[maxcost])];
if (d[v][newcost] > d[u][maxcost]+w)
{
d[v][newcost] = d[u][maxcost]+w;
q.push(State(v,d[v][newcost],newcost));
}
}
}
for (int t = 1 ; t <= n ; ++t)
{
int ret = inf;
for (int i = 1 ; i <= n ; ++i) if (ret > d[t][i]+f[i])
ret = d[t][i]+f[i];
if (ret==inf) ans[s][t] = -1;
else ans[s][t] = ret;
}
}

void solve()
{
for (int s = 1 ; s <= n ; ++s)
Dij(s);
int u , v;
while (q--)
{
scanf("%d%d",&u,&v);
printf("%d\n",ans[u][v]);
}
}

int main()
{
int k = 0;
bool first = true;
while (scanf("%d%d%d",&n,&m,&q),n+m,+q)
{
if (first) first = false;
else cout << endl;
++k;
init();
input();
printf("Case #%d\n",k);
solve();
}
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值