洛谷P4047 [JSOI2010]部落劃分 題解
阿新 • • 發佈:2021-01-08
[JSOI2010]部落劃分 - 洛谷
description:
給定平面直角座標系上的
個點,請將這 個點合併成 個集合,使得最終距離最小的集合距離最大。(兩個集合間的距離指的是其中最近元素的距離。
solution:
我們觀察到資料範圍較小,直接暴力兩兩點之間建邊。
然後我們相當於把一些點合併到另一些點當中,合併
條邊即可。跑最小生成樹。
code:
#include<cstdio>
#include<cmath>
#include<algorithm>
using namespace std;
struct ben
{
int x,y;
double val;
}a[1000005];
int cmp(const ben &a,const ben &b)
{
return a.val<b.val;
}
int fa[1005];
int find(int x)
{
if(fa[x]!=x)fa[x]=find(fa[x]);
return fa[x];
}
double x[1005],y[1005];
int main()
{
int n,k;
scanf("%d%d",&n,&k);
for(int i=1;i<=n;i++)
{
fa[i]=i;
scanf("%lf%lf",&x[i],&y[i]);
}
int cnt=0;
for(int i=1;i<=n;i++)
{
for(int j=i+1;j<=n;j++)
{
a[++cnt].x=i;
a[cnt].y=j;
a[cnt].val=sqrt((x[i]-x[j])*(x[i]-x[j])+(y[i]-y[j])*(y[i]-y[j]));
}
}
sort(a+1,a+cnt+1,cmp);
int sum=0;
for (int i=1;i<=cnt;i++)
{
int x=find(a[i].x);
int y=find(a[i].y);
if(x!=y)
{
fa[y]=x;
sum++;
}
if(sum==n-k+1)
{
printf("%.2lf\n",a[i].val);
break;
}
}
return 0;
}