Trucking |
Time Limit: 20000/10000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) |
Total Submission(s): 72 Accepted Submission(s): 28 |
|
Problem Description
A certain local trucking company would like to transport some
goods on a cargo truck from one place to another. It is desirable to
transport as much goods as possible each trip. Unfortunately, one cannot
always use the roads in the shortest route: some roads may have
obstacles (e.g. bridge overpass, tunnels) which limit heights of the
goods transported. Therefore, the company would like to transport as
much as possible each trip, and then choose the shortest route that can
be used to transport that amount.
For the given cargo truck, maximizing the height of the goods transported is equivalent to maximizing the amount of goods transported. For safety reasons, there is a certain height limit for the cargo truck which cannot be exceeded. |
Input
The input consists of a number of cases. Each case starts with
two integers, separated by a space, on a line. These two integers are
the number of cities (C) and the number of roads (R). There are at most
1000 cities, numbered from 1. This is followed by R lines each
containing the city numbers of the cities connected by that road, the
maximum height allowed on that road, and the length of that road. The
maximum height for each road is a positive integer, except that a height
of -1 indicates that there is no height limit on that road. The length
of each road is a positive integer at most 1000. Every road can be
travelled in both directions, and there is at most one road connecting
each distinct pair of cities. Finally, the last line of each case
consists of the start and end city numbers, as well as the height limit
(a positive integer) of the cargo truck. The input terminates when C = R
= 0.
|
Output
For each case, print the case number followed by the maximum
height of the cargo truck allowed and the length of the shortest route.
Use the format as shown in the sample output. If it is not possible to
reach the end city from the start city, print "cannot reach destination"
after the case number. Print a blank line between the output of the
cases.
|
Sample Input
5 6 1 2 7 5 1 3 4 2 2 4 -1 10 2 5 2 4 3 4 10 1 4 5 8 5 1 5 10 5 6 1 2 7 5 1 3 4 2 2 4 -1 10 2 5 2 4 3 4 10 1 4 5 8 5 1 5 4 3 1 1 2 -1 100 1 3 10 0 0 |
Sample Output
Case 1: maximum height = 7 length of shortest route = 20 Case 2: maximum height = 4 length of shortest route = 8 Case 3: cannot reach destination |
思路:题意:每一个地方有限高h,距离,车的最大载重量就是经过的地方限高的最小值,求这个最小值最大是多少,已经经过的路程
我们先二分这个h,判断mid是否合法,那么这样就可以做最短路时,做最短路时,判断mid是否小于限高即可啦,如果最后d[end]是INF,那么就不行,否则就行,
注意二分的边界!
1 #include <cstdio> 2 #include <cstring> 3 #include <iostream> 4 #include <cmath> 5 #include <algorithm> 6 #include <cstdlib> 7 #include <queue> 8 using namespace std; 9 10 const int maxn=1010,maxm=20010,INF=10000000; 11 struct qq 12 { 13 int n,to,z,h,ne; 14 friend bool operator < (qq a,qq b) 15 { 16 return a.z>b.z; 17 } 18 } e[maxm],s,ya; 19 20 priority_queue<qq> q; 21 int d[maxn],node,x,y,z,cnt,to,n,m,h[maxn]; 22 bool f[maxn]; 23 int ans,st,en,height,lim,cas,minn,maxx,mid; 24 25 void addedge(int x,int y,int z,int height) 26 { 27 cnt++; 28 e[cnt].n=x; 29 e[cnt].to=y; 30 e[cnt].z=z; 31 e[cnt].ne=h[x]; 32 e[cnt].h=height; 33 h[x]=cnt; 34 } 35 36 void close() 37 { 38 exit(0); 39 } 40 41 void dijkstra(int st,int k) 42 { 43 memset(f,false,sizeof(f)); 44 while (!q.empty()) 45 q.pop(); 46 f[st]=true; 47 for (int i=0;i<=n;i++) 48 d[i]=INF; 49 d[st]=0; 50 for (int p=h[st];p!=-1;p=e[p].ne) 51 { 52 s.n=st; 53 s.to=e[p].to; 54 s.z=e[p].z; 55 s.h=e[p].h; 56 if (s.h<k && s.h!=-1)//高度不够 57 continue; 58 q.push(s); 59 } 60 while (!q.empty()) 61 { 62 s=q.top(); 63 q.pop(); 64 to=s.to; 65 if (f[to]) continue; 66 d[to]=s.z; 67 f[to]=true; 68 for (int p=h[to];p!=-1;p=e[p].ne) 69 { 70 node=e[p].to; 71 if (not f[node]) 72 { 73 ya.n=to; 74 ya.to=node; 75 ya.z=d[to]+e[p].z; 76 ya.h=e[p].h; 77 if (ya.h<k && ya.h!=-1) //高度不够 78 continue; 79 q.push(ya); 80 } 81 } 82 } 83 } 84 85 bool judge(int mid) 86 { 87 dijkstra(st,mid); 88 if (d[en]!=INF) 89 return true; 90 return false; 91 } 92 93 void work() 94 { 95 if (not judge(1)) 96 { 97 printf("cannot reach destination\n"); 98 return; 99 } 100 minn=1;maxx=lim; 101 while (maxx>minn) 102 { 103 mid=(maxx+minn+1)>>1; 104 if (judge(mid)) // The height is accepted! 105 minn=mid; 106 else 107 maxx=mid-1; 108 } 109 judge(maxx); 110 printf("maximum height = %d\n",maxx); 111 printf("length of shortest route = %d\n",d[en]); 112 } 113 114 void init() 115 { 116 cas=0; 117 while (scanf("%d %d",&n,&m)!=EOF) 118 { 119 if (n==0 && m==0) break; 120 cas++; 121 if (cas!=1) 122 printf("\nCase %d:\n",cas); 123 else 124 printf("Case %d:\n",cas); 125 memset(h,-1,sizeof(h)); 126 cnt=0; 127 for (int i=1;i<=m;i++) 128 { 129 scanf("%d %d %d %d",&x,&y,&z,&height); 130 addedge(x,y,height,z); 131 addedge(y,x,height,z); 132 } 133 scanf("%d %d %d",&st,&en,&lim); 134 work(); 135 } 136 } 137 138 139 int main () 140 { 141 init(); 142 close(); 143 }