HDU-6705 path (bfs)

Problem Description

You have a directed weighted graph with n

vertexes and m

edges. The value of a path is the sum of the weight of the edges you passed. Note that you can pass any edge any times and every time you pass it you will gain the weight.

Now there are q

queries that you need to answer. Each of the queries is about the k-th minimum value of all the paths.

Input

The input consists of multiple test cases, starting with an integer t

(1≤t≤100)

, denoting the number of the test cases.
The first line of each test case contains three positive integers n,m,q. (1≤n,m,q≤5∗104)

Each of the next m

lines contains three integers ui,vi,wi

, indicating that the i−th

edge is from ui

to vi

and weighted wi

.(1≤ui,vi≤n,1≤wi≤109)

Each of the next q

lines contains one integer k

as mentioned above.(1≤k≤5∗104)

It‘s guaranteed that Σn

,Σm

, Σq,Σmax(k)≤2.5∗105

and max(k)

won‘t exceed the number of paths in the graph.

Output

For each query, print one integer indicates the answer in line.

Sample Input

1
2 2 2
1 2 1
2 1 2
3
4

Sample Output

3
3

Hint

1->2 value :1

2->1 value: 2

1-> 2-> 1 value: 3

2-> 1-> 2 value: 3

题意:题意很简单,就是给你一张单向图,求Q个询问,问整个图的第Q【i】长度路径

思路:开始的时候,是直接暴力添边,直到第k大,但是寻思可能MLE,自作聪明的对队列限制只能加入MAXX个(最大的询问值),超过了就直接和队列的最大值比较。

但是这样是TLE的,因为可能会有菊花图,对于一个点如果直接扩展其所有连边就容易TLE. 复杂度 T*k*log(k*n)

所以我们考虑,对于一条已知的最小边,需要如何扩展,很明显我们可以拓展其出点的最小出边,这肯定是下一个最小的候选答案,因为该边是由入点扩展的一条边,那么如果该入点还有比该边权值大的边,也扩展它,这样就保证了最小的边一定被扩展出来了,后面重复过程,直到计算完MAXX.

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3
 4 const int maxn = 5e4+5;
 5 int n,m,k,t,q;
 6 typedef pair<int,int>p;
 7 typedef long long ll;
 8 vector<p>node[maxn];
 9
10 ll ans[maxn];
11 int Q[maxn];
12
13 struct Point
14 {
15     ll val;
16     int now,id;
17     Point(ll val,int now,int id):val(val),now(now),id(id){}
18     bool operator<(const Point &b)const{
19         return val > b.val;
20     }
21 };
22
23 priority_queue<Point>que;
24 void bfs(int limit)
25 {
26     while(!que.empty())que.pop();
27    for(int i=1;i<=n;i++)sort(node[i].begin(),node[i].end());
28    for(int i=1;i<=n;i++)
29    {
30        if(!node[i].empty())que.push(Point(node[i][0].first,i,0));
31    }
32     int tot = 0;
33     while(!que.empty())
34     {
35         Point tmp = que.top();
36         que.pop();
37         ll cost = tmp.val;
38         int now = tmp.now;
39         int id = tmp.id;
40         if(++tot > limit)return;
41         ans[tot] = cost;
42         if(id < node[now].size() - 1)
43         {
44             que.push(Point(cost-node[now][id].first+node[now][id+1].first,now,id+1));
45         }
46         if(!node[node[now][id].second].empty())
47         {
48             que.push(Point(cost+node[node[now][id].second][0].first,node[now][id].second,0));
49         }
50     }
51 }
52
53 int main()
54 {
55     scanf("%d",&t);
56     while(t--)
57     {
58         scanf("%d%d%d",&n,&m,&q);
59         int maxx = 0;
60         for(int i=1;i<=n;i++)node[i].clear();
61         for(int i=1;i<=m;i++)
62         {
63             int u,v,w;
64             scanf("%d%d%d",&u,&v,&w);
65             node[u].push_back(p(w,v));
66         }
67         for(int i=1;i<=q;i++)
68         {
69             scanf("%d",&Q[i]);
70             maxx = max(maxx,Q[i]);
71         }
72         bfs(maxx);
73         for(int i=1;i<=q;i++)
74         {
75             printf("%lld\n",ans[Q[i]]);
76         }
77     }
78 }

原文地址:https://www.cnblogs.com/iwannabe/p/11402800.html

时间: 2024-10-12 21:37:17

HDU-6705 path (bfs)的相关文章

HDU 1495 非常可乐 (BFS)

 问题链接:http://acm.hdu.edu.cn/showproblem.php?pid=1495 题目大意:一个瓶子容积s,两个杯子容积分别n,m,并且都没有刻度(不能比对噢!).相互倒水,求平分的他们的最少倒水次数. 思路:暴力搜索吧.并且求最少,(即最优解),所以上BFS: 思考:状态,转移过程,怎么剪纸. 惨痛的debug,我不解释了. 源代码: #include<iostream> #include<cstdio> #include<queue> #

HDU - 1973 - Prime Path (BFS)

Prime Path Time Limit: 5000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 987    Accepted Submission(s): 635 Problem Description The ministers of the cabinet were quite upset by the message from the Chief of S

HDU 1495 非常可乐(BFS)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1495 Problem Description 大家一定觉的运动以后喝可乐是一件很惬意的事情,但是seeyou却不这么认为.因为每次当seeyou买了可乐以后,阿牛就要求和seeyou一起分享这一瓶可乐,而且一定要喝的和seeyou一样多.但seeyou的手中只有两个杯子,它们的容量分别是N 毫升和M 毫升 可乐的体积为S (S<101)毫升 (正好装满一瓶) ,它们三个之间可以相互倒可乐 (都是没有

HDU 1175 连连看(BFS)

Problem Description “连连看”相信很多人都玩过.没玩过也没关系,下面我给大家介绍一下游戏规则:在一个棋盘中,放了很多的棋子.如果某两个相同的棋子,可以通过一条线连起来(这条线不能经过其它棋子),而且线的转折次数不超过两次,那么这两个棋子就可以在棋盘上消去.不好意思,由于我以前没有玩过连连看,咨询了同学的意见,连线不能从外面绕过去的,但事实上这是错的.现在已经酿成大祸,就只能将错就错了,连线不能从外围绕过.玩家鼠标先后点击两块棋子,试图将他们消去,然后游戏的后台判断这两个方格能

hdu 1401 双向搜索(bfs)

题意是给你两个棋盘格局   问由第一个最多搜8步能不能到达第二个格局: 单项广搜应该能做    注意优化就行   我是想练一下双向  所以这里就只说下双向的吧: 和普通搜索一样    但由于起点终点的地位一样 (及起点也可以是终点,不要求求最小步数)  这样就可以让起点和终点各走4步   看有没有遇到的地方: 注意  这里的4个棋子都是一样的,导致你标记的时候不能简单的直接进行标记   (为此贡献了几次wa   唉  只怪当初太年轻)   我的处理上把4个棋子进行排序然后进行标记   标记数组开

HDU 5012 Dice (BFS)

其实是很水的一道bfs,用字符串表示每个状态,map判重就ok了. 题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5012 #include<iostream> #include<cstdio> #include<cstring> #include<cmath> #include<cctype> #include<algorithm> #include<string> #in

POJ 3126 Prime Path(BFS)

Prime Path Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 12060   Accepted: 6843 Description The ministers of the cabinet were quite upset by the message from the Chief of Security stating that they would all have to change the four-dig

poj3126——Prime Path(BFS)

Description The ministers of the cabinet were quite upset by the message from the Chief of Security stating that they would all have to change the four-digit room numbers on their offices. - It is a matter of security to change such things every now

POJ 3216 Prime Path (BFS)

The ministers of the cabinet were quite upset by the message from the Chief of Security stating that they would all have to change the four-digit room numbers on their offices. — It is a matter of security to change such things every now and then, to