分类:图论,生成树,最短路,并查集
作者:ACShiryu
时间:2011-7-28
地址:ACShiryu's Blog
Heavy Transportation
Time Limit: 3000MS Memory Limit: 30000K
Total Submissions: 11929 Accepted: 3171

Description

Background 
Hugo Heavy is happy. After the breakdown of the Cargolifter project he can now expand business. But he needs a clever man who tells him whether there really is a way from the place his customer has build his giant steel crane to the place where it is needed on which all streets can carry the weight. 
Fortunately he already has a plan of the city with all streets and bridges and all the allowed weights.Unfortunately he has no idea how to find the the maximum weight capacity in order to tell his customer how heavy the crane may become. But you surely know.

Problem 
You are given the plan of the city, described by the streets (with weight limits) between the crossings, which are numbered from 1 to n. Your task is to find the maximum weight that can be transported from crossing 1 (Hugo's place) to crossing n (the customer's place). You may assume that there is at least one path. All streets can be travelled in both directions.

Input

The first line contains the number of scenarios (city plans). For each city the number n of street crossings (1 <= n <= 1000) and number m of streets are given on the first line. The following m lines contain triples of integers specifying start and end crossing of the street and the maximum allowed weight, which is positive and not larger than 1000000. There will be at most one street between each pair of crossings.

Output

The output for every scenario begins with a line containing "Scenario #i:", where i is the number of the scenario starting at 1. Then print a single line containing the maximum allowed weight that Hugo can transport to the customer. Terminate the output for the scenario with a blank line.

Sample Input

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

Sample Output

Scenario #1:
4
题目大意是就是何处一个图,n个顶点和m条边,每个边都有最大承载量,现在我要从1点运送货物到n点,求能运送货物的最大重量。
对于数据,第一行为t代表测试数据个数,第二行为n和m(意义见上),接着m行,每行三个整数分别是代表一条边的起点,终点及最大承重量。输出能运送货物的最大重量,格式见样例。注意数据输完后还要再多输一个空行。
对于数据,从1运到3有两种方案
方案1:1-2-3,其中1-2承重为3,2-3承重为5,则可以运送货物的最大重量是3(当大于3时明显1到不了2)
方案2:1-3,可知1-3承重为4,故此路可运送货物的最大重量是4,故答案输出4
因为此前也没做过图论题,对一些算法都不熟,再刚开始题意理解有问题,WA了几次,看懂题意后,搜了下别人的解题报告,说是Dijkstra的变形或这求最大生成树。也许对Dijkstra运用(压根就没用过)的不是很熟,一直不知道怎么下手,连样列都过不了。后就直接转到求最大生成树上去了,网上大部分代码是Prim算法,由于《算法入门竞赛经典》书没介绍该算法,暂时还没看,所以就选择Kruskal求最大生成树。然后选择Kruskal的一个问题就是连通分量的处理,《入门经典》是用的并查集来处理,因为对生成树算法不是很熟,就直接套的上面的模板。然后题目就是编程了求最大生成树,并找出从1-n的最小权值的边。当然,这棵树不用搜完,因为,你从1到n不一定会每一个节点都走过,当将1-n连通时此时的权值就是所求的值;转换用Kruskal时因为数组开大了MLE一次,开小了RE一次,最后决定还是动态分配靠谱些。不过因为一个小细节又WA了一次,最后改正,终于AC了,你说,AC一题我容易不!!!总之ACM搞图论的上辈子都是折翼的天使!!!

如果有时间,这题还会再做一遍的,用Prim算法和Dijkstra试一下!

参考代码:

 1 //第一次提交的代码基本是套模板的,和自己写的出入较大,不习惯,将代码修改下感觉也许更好!,第一次提交的代码见最下面 2 #include<iostream> 3 #include<cstdlib> 4 #include<cstdio> 5 #include<cstring> 6 #include<algorithm> 7 #include<cmath> 8 using namespace std; 9 const int inf = (1<<20);10 int p[1005];        //p是用于并查集的,r是用来存储边序号的11 struct prog {12     int w,v,u;        //记录起点,终点,权值13 };14 bool cmp(prog a,prog b)15 {//间接排序函数,16     return a.w>b.w;17 }18 int find(int x)19 {//并查集里的find函数,你懂的20     return p[x]==x?x:p[x]=find(p[x]);21 }22 int main()23 {24     int t;25     cin >> t;26     int k = 1;27     while(t--)28     {29         int n ,m;30         cin >> n >> m;31         prog *r;32         r=new prog[m];33         int i ;34         for ( i = 0 ; i < m ; i ++ )35             cin>>r[i].u>>r[i].v>>r[i].w;    //输入边的信息36 37         for ( i =1 ; i <= n; i ++ )38             p[i]=i;//初始化并查集39 40         sort(r,r+m,cmp);//根据边的权值的大小将边的序号进行排序,r[i]表示第i+1大的边存储在u,v,w数组中的序号41         int ans=inf;    //将答案初始化为最大值42         for ( i = 0 ; i < m ; i ++ )43         {44             int x=find(r[i].u);45             int y=find(r[i].v);46             if(x!=y)47             {//如果该边所在的两边不在同一个连通分量里,则连接该边48                 if(ans>r[i].w)//如果该边的权值比ans小(实际上一定不会比ans大),则更新ans49                     ans=r[i].w;50                 p[x]=y;//连接该边51                 if(find(1)==find(n))//当1和n连通时,则说明找到了一条从1到n的路,并且可知该路的所有边的权值都是最大的,故边的最小权值就是答案52                     break;53             }54         }55         //输出答案,格式如题所述56         cout<<"Scenario #"<<k<<":"<<endl;57         cout<<ans<<endl<<endl;58         k++;59     }60     return 0;61 }

  附:第一次参考代码

 1 #include<iostream> 2 #include<cstdlib> 3 #include<cstdio> 4 #include<cstring> 5 #include<algorithm> 6 #include<cmath> 7 using namespace std; 8 const int inf = (1<<20); 9 int *p,*r;        //p是用于并查集的,r是用来存储边序号的10 int *u,*v,*w;    //分别代表边的起点,终点,和权值,明显不是我的风格,先熟悉下模板,不得不这样写11 bool cmp(const int a,const int b)12 {//间接排序函数,13     return w[a]>w[b];14 }15 int find(int x)16 {//并查集里的find函数,你懂的17     return p[x]==x?x:p[x]=find(p[x]);18 }19 int main()20 {21     int t;22     cin >> t;23     int k = 1;24     while(t--)25     {26         int n ,m;27         cin >> n >> m;28         int i ;29         u=new int[m];30         v=new int[m];31         w=new int[m];32         r=new int[m];//动态分配33         for ( i = 0 ; i < m ; i ++ )34         {35             int a , b , c ;36             cin>>a>>b>>c;37             u[i]=a;38             v[i]=b;39             w[i]=c;//加入边40         }41         p=new int[n+1];42         for ( i =1 ; i <= n; i ++ )43             p[i]=i;//初始化并查集44         for ( i = 0 ;i < m ; i ++ )45             r[i]=i;//初始化边序号46         sort(r,r+m,cmp);//根据边的权值的大小将边的序号进行排序,r[i]表示第i+1大的边存储在u,v,w数组中的序号47         int ans=inf;    //将答案初始化为最大值48         for ( i = 0 ; i < m ; i ++ )49         {50             int e=r[i];//找到第i+1大的边51             int x=find(u[e]);52             int y=find(v[e]);53             if(x!=y)54             {//如果该边所在的两边不在同一个连通分量里,则连接该边55                 if(ans>w[e])//如果该边的权值比ans小(实际上一定不会比ans大),则更新ans56                     ans=w[e];57                 p[x]=y;//连接该边58                 if(find(1)==find(n))//当1和n连通时,则说明找到了一条从1到n的路,并且可知该路的所有边的权值都是最大的,故边的最小权值就是答案59                     break;60             }61         }62         //输出答案,格式如题所述63         cout<<"Scenario #"<<k<<":"<<endl;64         cout<<ans<<endl<<endl;65         k++;66     }67     return 0;68 }

转载于:https://www.cnblogs.com/ACShiryu/archive/2011/07/28/2119812.html

POJ 1797 Heavy Transportation 解题报告相关推荐

  1. POJ 1797 Heavy Transportation

    传送门:http://poj.org/problem?id=1797 不想吐槽了,弄了好久才AC 实现代码: #include <cstdio> #include <cstring& ...

  2. (Realx dijkstra1.1)POJ 1797 Heavy Transportation(使用dijkstra来解决最大生成树问题)

    题目大意:有n个城市,m条道路,在每条道路上有一个承载量,现在要求从1到n城市最大承载量,而最大承载量就是从城市1到城市n所有通路上的最大承载量 解题思路:其实这个求最大边可以近似于求最短路,只要修改 ...

  3. POJ 1797 Heavy Transportation

    题意: 给出一个有N个节点的无向图和 M 条边,每条边都有一个重力承受度,要从中找出一条从 1 节点到 n节点的路径,使得可以经过的车辆载重最大. 分析: 类似于最大流中找增广路,在求最短路的松弛操作 ...

  4. POJ 1797 Heavy Transportation 最短路变形(dijkstra算法)

    题目:click here 题意: 有n个城市,m条道路,在每条道路上有一个承载量,现在要求从1到n城市最大承载量,而最大承载量就是从城市1到城市n所有通路上的最大承载量. 分析: 其实这个求最大边可 ...

  5. POJ 2800 垂直直方图 解题报告

    POJ 2800 垂直直方图 解题报告 编号:2800   考查点:简单计算题 思路: 用gets()读入4行数据,然后按字符统计,显示的时候有点小处理即可. 提交情况: 感觉POJ的测试数据有点骗人 ...

  6. Tarjan算法求解桥和边双连通分量(附POJ 3352 Road Construction解题报告)

    http://blog.csdn.net/geniusluzh/article/details/6619575 在说Tarjan算法解决桥和边双连通分量问题之前我们先来回顾一下Tarjan算法是如何求 ...

  7. POJ 2977 生理周期 解题报告

    2977 : 生理周期 总时间限制: 1000ms 内存限制: 65536kB 描述 人生来就有三个生理周期,分别为体力.感情和智力周期,它们的周期长度为23天.28天和33天.每一个周期中有一天是高 ...

  8. POJ 1001 Exponentiation C++解题报告 JAVA解题报告

    求高精度幂 Time Limit: 500MS   Memory Limit: 10000K Total Submissions: 126980   Accepted: 30980 Descripti ...

  9. poj 2182 Lost Cows 解题报告

    题意:每个奶牛都有一个编号,1- N 从第二个牛开始给出前面比她编号小的牛的个数,问你求牛的编号序列 解题思路:线段树+ 二分查找 (多个相同的数二分边界问题需要注意) 解题代码: 1 #includ ...

最新文章

  1. 非线性方程求根的牛顿法
  2. 好用的 php类,一个好用的php文件上传处理类
  3. 10个重要的Linux ps命令实战
  4. .NET Core 2.1 容器镜像将从 Docker Hub 中删除
  5. MySQL性能医生:Orzdba工具安装和使用
  6. 【刷算法】按照之字形打印二叉树
  7. Js 通过点击改变css样式
  8. nvm装node npm
  9. C语言编写猜数字小游戏
  10. GitHub客户端上传本地代码
  11. 草图大师SketchUp2016下载和安装教程
  12. 【python】pandas的excel处理:员工薪水分析
  13. WPS-Word:下一页分节符不能分页,插入下一页分节符时下一节没有在新的一页开始
  14. 访问者模式(Vistor)
  15. win10、win7“以太网”将WiFi名称改成网络名称
  16. java swing漂亮界面框架_开源软件分享-漂亮的JavaFx GUI界面框架
  17. 第三方SDK接入--微信
  18. 余弦定理对比文本相似度实现查重
  19. mysql 实现lead_MYSQL 代替lead()的寫法?
  20. invalid python sd,Fatal Python error: init_fs_encoding: failed to get the Python cod如何解决

热门文章

  1. Js正则表达式数字或者带小数点的数字
  2. vue --- 获取子组件数据的一个应急方案$refs
  3. 一条命令教你安装centos下面的pip服务
  4. 浙企加入中国大数据产业生态联盟 共商数据价值
  5. Spring JPA 中的Repository体系
  6. C语言--在终端输入多行信息,找出包含“ould”的行,并打印改行
  7. GoLang之方法与接口
  8. [翻译] BFKit
  9. PrimeTime指南——概述和基本流程
  10. 【Python学习】——语言风格(变量赋值、深浅拷贝、for循环陷阱)