把博客园图标替换成自己的图标
把博客园图标替换成自己的图标end

【二分答案/最小生成树】部落划分(洛谷P4047)

题目描述

输入

第一行包含两个整数N、K,分别描述野人居住点的数量和部落的数量。
接下来N 行,每行包含两个整数xi, yi,描述了一个居住点的坐标。

输出

输出一行,为最优划分时,最近的两个部落的距离,精确到小数点后两位。

数据范围限制

 

Solution:

第一眼看到最小最大就秒写二分答案,结果爆精度了QAQ

正解有两个,一个是二分答案,不难发现单调性,二分结果,check的时候就判断各个点之间距离是否有小于二分出来答案的,有就把两点合并,运用并查集即可解决,但是要注意精度问题(详见代码)

另一个说是最小生成树,其实是运用类似于kruscal的思想,sort点点之间边的长度,然后从最小的开始判断,并使用并查集将它们合并,同时动态更新并查集数量,当并查集数量等于K即划分完毕

Code(二分答案):

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 int N,K,Book[10005],Ans,fa[10005];
 4 double Dis[1005][1005],X[10005],Y[10005];
 5 int find(int x)
 6 {
 7     if(fa[x]==x) return x;
 8     else return fa[x]=find(fa[x]);
 9 }
10 bool Check(double T){
11     Ans=0;
12     for(int i=1;i<=N;i++) fa[i]=i;
13     for(int i=1;i<=N;i++) Book[i]=0;
14 //    double Test=T+0.005;
15     for(int i=1;i<N;i++)
16         for(int j=i+1;j<=N;j++){
17             if(T>Dis[i][j]){
18                 int fx=find(i),fy=find(j);
19                 if(fx!=fy)
20                     fa[fx]=fy;
21             }
22         }
23     for(int i=1;i<=N;i++){
24         int father=find(i);
25         if(!Book[father]){
26             Ans++;
27             Book[father]=1;
28         }
29     }
30     if(Ans>=K) return true;
31     else return false;
32     
33 }
34 int main()
35 {
36 //    freopen("tribe.in","r",stdin);
37 //    freopen("tribe.out","w",stdout);
38     scanf("%d%d",&N,&K);
39     for(int i=1;i<=N;i++)
40         scanf("%lf%lf",&X[i],&Y[i]);
41     for(int i=1;i<=N;i++)
42         for(int j=1;j<=N;j++){
43             Dis[i][j]=sqrt((X[i]-X[j])*(X[i]-X[j])+(Y[i]-Y[j])*(Y[i]-Y[j]));
44     //        Dis[i][j]+=0.005;
45         }
46     double L=0.0001,R=200000000.00,Res=0;
47     while(L-R<=0.0001){
48         double Mid=(L+R)/2;
49         if(Check(Mid)){
50             Res=Mid;
51             L=Mid+0.0001;
52         }
53         else
54             R=Mid-0.0001;
55     }
56 
57     printf("%.2lf",Res);
58     return 0;
59 }

 

posted @ 2020-08-24 21:00  fluoce  阅读(169)  评论(0编辑  收藏  举报

Contact with me