Highways POJ

The island nation of Flatopia is perfectly flat. Unfortunately, Flatopia has a very poor system of public highways. The Flatopian government is aware of this problem and has already constructed a number of highways connecting some of the most important towns. However, there are still some towns that you can't reach via a highway. It is necessary to build more highways so that it will be possible to drive between any pair of towns without leaving the highway system. 

Flatopian towns are numbered from 1 to N and town i has a position given by the Cartesian coordinates (xi, yi). Each highway connects exaclty two towns. All highways (both the original ones and the ones that are to be built) follow straight lines, and thus their length is equal to Cartesian distance between towns. All highways can be used in both directions. Highways can freely cross each other, but a driver can only switch between highways at a town that is located at the end of both highways. 

The Flatopian government wants to minimize the cost of building new highways. However, they want to guarantee that every town is highway-reachable from every other town. Since Flatopia is so flat, the cost of a highway is always proportional to its length. Thus, the least expensive highway system will be the one that minimizes the total highways length. 

Input

The input consists of two parts. The first part describes all towns in the country, and the second part describes all of the highways that have already been built. 

The first line of the input file contains a single integer N (1 <= N <= 750), representing the number of towns. The next N lines each contain two integers, xi and yi separated by a space. These values give the coordinates of i thtown (for i from 1 to N). Coordinates will have an absolute value no greater than 10000. Every town has a unique location. 

The next line contains a single integer M (0 <= M <= 1000), representing the number of existing highways. The next M lines each contain a pair of integers separated by a space. These two integers give a pair of town numbers which are already connected by a highway. Each pair of towns is connected by at most one highway. 

Output

Write to the output a single line for each new highway that should be built in order to connect all towns with minimal possible total length of new highways. Each highway should be presented by printing town numbers that this highway connects, separated by a space. 

If no new highways need to be built (all towns are already connected), then the output file should be created but it should be empty. 

Sample Input

9
1 5
0 0 
3 2
4 5
5 1
0 4
5 2
1 2
5 3
3
1 3
9 7
1 2

Sample Output

1 6
3 7
4 9
5 7
8 3

题意:有大概750个点,点与点之间用道路连接,道路的长度就是点之间的直线距离
输入第一行为点数n,然后往下为n行,每行都是一个点的坐标,然后有一个数字m表示已经修建好的道路数,往下m行为修好道路的两头的村庄,
输出:问在保证所有的点都能连接的情况下,最少还有需要修建多少条新道路,把这些新道路连接的两头村庄按格式输出

思路:一个比较简单的最小生成树的题,只需要把点的坐标转换成距离,然后存入容器中按照Kruskal算法写即可。
有一个比较奇怪的想象:我是在vj上写的同一个代码用c++提交超时,但改用G++提交就ac了

代码:
  1 #include <cstdio>
  2 #include <fstream>
  3 #include <algorithm>
  4 #include <cmath>
  5 #include <deque>
  6 #include <vector>
  7 #include <queue>
  8 #include <string>
  9 #include <cstring>
 10 #include <map>
 11 #include <stack>
 12 #include <set>
 13 #include <sstream>
 14 #include <iostream>
 15 #define mod 998244353
 16 #define eps 1e-6
 17 #define ll long long
 18 #define INF 0x3f3f3f3f
 19 using namespace std;
 20 
 21 //u表示起点,v表示终点,cost表示花费
 22 struct node
 23 {
 24     int u,v;
 25     double cost;
 26 };
 27 //排序,从小到大
 28 bool cmp(node a,node b)
 29 {
 30     return a.cost<b.cost;
 31 }
 32 //存放边的信息
 33 vector<node> ve;
 34 
 35 //fa表示当前i的最远祖先
 36 int fa[755];
 37 //初始化fa,开始时自己是自己的祖先
 38 void init(int qwq)
 39 {
 40     for(int i=0;i<=qwq;i++)
 41     {
 42         fa[i]=i;
 43     }
 44 }
 45 //查找最远祖先,同时进行路径压缩
 46 int find(int x)
 47 {
 48     if(fa[x]==x)
 49     {
 50         return x;
 51     }
 52     return fa[x]=find(fa[x]);
 53 }
 54 //判断最远祖先是否相同
 55 bool che(int x,int y)
 56 {
 57     return find(x)==find(y);
 58 }
 59 //合并x,y,把他们放到同一个家族中
 60 void mer(int x,int y)
 61 {
 62     if(!che(x,y)) 
 63     {
 64         fa[fa[x]]=fa[y];
 65     }
 66     return ;
 67 }
 68 int n,m;
 69 struct dian
 70 {
 71     int x,y;
 72 };
 73 dian di[755];
 74 //求两点之间的距离
 75 double dist(dian a,dian b)
 76 {
 77     return sqrt(double(a.x-b.x)*(a.x-b.x)+double(a.y-b.y)*(a.y-b.y));
 78 }
 79 int main()
 80 {
 81     scanf("%d",&n);
 82     //初始化
 83     init(n);
 84     for(int i=1;i<=n;i++)
 85     {
 86         scanf("%d %d",&di[i].x,&di[i].y);
 87     }
 88 
 89     scanf("%d",&m);
 90     int a,b;
 91     for(int i=0;i<m;i++)
 92     {
 93         scanf("%d %d",&a,&b);
 94         //让已经连接的道路合并在一个集合中
 95         mer(a,b);
 96     }
 97     node no;
 98     //将坐标信息转换成距离并存放到容器中
 99     for(int i=1;i<n;i++)
100     {
101         for(int j=i+1;j<=n;j++)
102         {
103             no.u=i;
104             no.v=j;
105             no.cost=dist(di[i],di[j]);
106             ve.push_back(no);
107         }
108     }
109     //排序
110     sort(ve.begin(),ve.end(),cmp);
111     for(int i=0;i<ve.size();i++)
112     {
113         if(!che(ve[i].u,ve[i].v))
114         {
115             mer(ve[i].u,ve[i].v);
116             //输入
117             printf("%d %d
",ve[i].u,ve[i].v);
118         }
119     }
120     //清除容器空间
121     ve.clear();
122 }
原文地址:https://www.cnblogs.com/mzchuan/p/11736866.html