Description
国防部计划用无线网络连接若干个边防哨所。2种不同的通讯技术用来搭建无线网络; 每个边防哨所都要配备无线电收发器;有一些哨所还可以增配卫星电话。 任意两个配备了一条卫星电话线路的哨所(两边都拥有卫星电话)均可以通话,无论 他们相距多远。而只通过无线电收发器通话的哨所之间的距离不能超过D,这是受收发器的功率限制。收发器的功率越高,通话距离D会更远,但同时价格也会更贵。 收发器需要统一购买和安装,所以全部哨所只能选择安装一种型号的收发器。换句话说,每一对哨所之间的通话距离都是同一个D。 你的任务是确定收发器必须的最小通话距离D,使得每一对哨所之间至少有一条通话路径(直接的或者间接的)。
Input
第 1 行:2个整数 S(1<=S<=100)和 P(S<P<=500), S表示可安装的卫星电话的哨 所数,P表示边防哨所的数量。 接下里P行,每行描述一个哨所的平面坐标(x,y),以 km为单位,整数,0<=x,y<=10000。
Output
第1行:1个实数D,表示无线电收发器的最小传输距离。精确到小数点后两位。
Range
对于20%的数据 P=2,S=1 对于另外20%的数据 P=4,S=2 对于100%的数据 1<=S<=100,S<P<=500
Solution
我们可以把这道题抽象一下,能通过收发器连接的哨所看成一个联通块,而卫星电话就代表可以连接联通块的边。所以这题就变成了最小生成树问题,即通过连边构造出P-S个联通块即可。
Code
#include<cmath> #include<cstdio> #include<cctype> #include<cstdlib> #include<algorithm> #define int long long using namespace std; int m,n,maxn,ans,cnt,sum; int father[505]; struct Node{ int x,y,dis; friend bool operator<(Node a,Node b){ return a.dis<b.dis; } }edge[250005]; struct Edge{ int x,y; }node[505]; int dist(int i,int j){ return (node[i].x-node[j].x)*(node[i].x-node[j].x)+(node[i].y-node[j].y)*(node[i].y-node[j].y); } int find(int x){ if(father[x]==x) return x; father[x]=find(father[x]); return father[x]; } int read(int &x){ x=0;char ch=getchar(); while(!isdigit(ch)) ch=getchar(); while(isdigit(ch)) x=(x<<1)+(x<<3)+(ch^48),ch=getchar(); } signed main(){ /*freopen("wireless.in","r",stdin); freopen("wireless.out","w",stdout);*/ read(m),read(n); for(int i=1;i<=n;i++) read(node[i].x),read(node[i].y); for(int i=1;i<=n;i++){ for(int j=1;j<=n;j++){ if(i==j) continue; edge[++cnt].x=i,edge[cnt].y=j; edge[cnt].dis=dist(i,j); } } sort(edge+1,edge+1+cnt); int k=0; for(int i=1;i<=n;i++) father[i]=i; for(int i=1;i<=cnt;i++){ int r1=find(edge[i].x); int r2=find(edge[i].y); if(r1!=r2) father[r1]=r2,k++; if(k+m==n){ printf("%.2lf",sqrt((double)edge[i].dis)); fclose(stdin);fclose(stdout); return 0; } } /*for(int i=sum;i;i--){ m-=2; if(have[edge[used[i]].x]) m++; if(have[edge[used[i]].y]) m++; have[edge[used[i]].x]=have[edge[used[i]].y]=1; if(m<0){ printf("%.2lf",sqrt((double)edge[used[i]].dis)); //fclose(stdin);fclose(stdout); return 0; } }*/ }
原文地址:https://www.cnblogs.com/YoungNeal/p/8483723.html
时间: 2024-10-15 02:27:14