您的位置:首页 > Web前端 > JavaScript

BZOJ1821 [JSOI2010]Group 部落划分 贪心+并查集

2017-12-23 17:36 447 查看
平面上有N个部落,使划分成K个居住点后,最近的两个居住点之间的距离最远。两个部落的距离,定义为部落中距离最近的那两个居住点的距离。求这个距离。

将完全图的边按照距离从小到大排序,选中边的两端用并查集并起来,第N-K+1条边的长度即为答案.

这个题目不需要二分,贪心比较巧妙

#include <bits/stdc++.h>
#define LL long long
#define clr(x,i) memset(x,i,sizeof(x))
using namespace std;
const int N=1005;
struct Edge{
int u,v;
double dist;
friend bool operator <(Edge a,Edge b){
return a.dist<b.dist;
}
}e[N*N*2];
int n,K,tot,fa
;
double x
,y
;
inline double Dis(int a,int b)
{
return sqrt((x[a]-x[b])*(x[a]-x[b])+(y[a]-y[b])*(y[a]-y[b]));
}
inline void Add(int u,int v)
{
e[++tot].u=u;e[tot].v=v;e[tot].dist=Dis(u,v);
}
int find(int v)
{
return fa[v]==v ? v : fa[v]=find(fa[v]);
}
int main()
{
scanf("%d%d",&n,&K);
for(int i=1;i<=n;i++)
scanf("%lf%lf",&x[i],&y[i]);
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)if(i!=j)
Add(i,j);
sort(e+1,e+tot+1);
for(int i=1;i<=n;i++)fa[i]=i;
int cnt=0;
for(int i=1;i<=tot;i++)
{
int x=find(e[i].u),y=find(e[i].v);
if(x!=y){
cnt++;fa[x]=y;
if(cnt==n-K+1){
printf("%.2lf",e[i].dist);
break;
}
}
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: