方法一:套路性的,二分距离,然后把距离点对距离小于答案的边都联通起来,然后看集合数量超过k说明答案小,增大,否则减小。

方法二:贪心,类kruskal。n个点,k个连通块,则需要有效连接(同一个块内的点相互连接不算)n-k次。那么用类似kruskal的证明过程发现最小的边一定要联通使得集合与集合间距离尽量大,连完n-k条边之后的第n-k+1条连接不同连通块的点对距离即为所求。

code是我一年前写的,现在我只能想出第一种方法,越学越退步,自闭嘤嘤嘤。

 //注:原来代码被我想复杂了,自己对比。
#include<bits/stdc++.h>
using namespace std;
typedef double db;
const int N=+;
inline int read(){
int x=,f=;char ch;
while(!isdigit(ch=getchar()))if(ch=='-') f=;
while(isdigit(ch)) x=(x<<)+(x<<)+(ch^''),ch=getchar();
return f?-x:x;
}
struct edge{
int u,v;db dis;
}e[N*N];
int X[N],Y[N],f[N];
int n,k,m,cnt; bool cmp(edge a,edge b){return a.dis<b.dis;}
int Find(int x){if(f[x]!=x) f[x]=Find(f[x]);return f[x];} int main(){
n=read(),k=read();
for(register int i=;i<=n;++i){
X[i]=read(),Y[i]=read();f[i]=i;
for(register int j=;j<i;++j) e[++m].dis=sqrt((Y[i]-Y[j])*(Y[i]-Y[j])+(X[i]-X[j])*(X[i]-X[j])),e[m].u=i,e[m].v=j;
}
sort(e+,e+m+,cmp);
for(register int i=;i<=m;++i){
int fx=Find(e[i].u),fy=Find(e[i].v);
if(fx!=fy){
f[fy]=fx,++cnt;
if(cnt==n-k+){printf("%.2f\n",e[i].dis);return ;}
}
}
return ;
}

最新文章

  1. 关于最近在做的一个js全屏轮播插件
  2. 103. Binary Tree Zigzag Level Order Traversal
  3. 1Android系统移植与驱动开发概述
  4. HDU 1024 (不重叠m段最大和) Max Sum Plus Plus
  5. Java 8 VM GC Tunning Guide Charter 5
  6. textarea中的文字自动换行问题
  7. 基于jqUI的日期选择(‘yy-mm-dd’)
  8. xtrabackup备份mysql数据库的使用方法
  9. 利用Vim提供的正则去掉代码每行开头不想要的行号以及vi常见问题和应用技巧
  10. 在linux系统中
  11. ListView中ConvertView和ViewHolder
  12. Mac包管理神器Homebrew
  13. 安卓和java开发环境的安装
  14. 去除inline-block出现间距的几种方法
  15. Vue学习入门
  16. jquery下的正反选操作
  17. web界面 之 登录 (初稿)
  18. cdn刷新和对应的浏览器现象
  19. NET MVC Bundling and RequireJS
  20. 左连接sql

热门文章

  1. centos7 的system
  2. jQuery 虚拟数字键盘代码
  3. 通过SublimeCodeIntel设置JavaScript自动补全
  4. SpringBoot集成MybatisPlus报错
  5. spring-boot 几个工具类(七)
  6. linux系统设置允许密码登录
  7. luogu P3959(2017noipTG D2T2
  8. win32多线程: 线程创建与结束等待
  9. Swoft2.x 小白学习笔记 (四) --- RPC
  10. array_merge与数组加