1. 程式人生 > >洛谷 1821: [JSOI2010]Group 部落劃分 Group

洛谷 1821: [JSOI2010]Group 部落劃分 Group

mem 錯誤 pac php group 輸出 tput 附近 可能

1821: [JSOI2010]Group 部落劃分 Group

Time Limit: 10 Sec Memory Limit: 64 MB
Submit: 2596 Solved: 1221
[Submit][Status][Discuss]

Description

聰聰研究發現,荒島野人總是過著群居的生活,但是,並不是整個荒島上的所有野人都屬於同一個部落,野人們總是拉幫結派形成屬於自己的部落,不同的部落之間則經常發生爭鬥。只是,這一切都成為謎團了——聰聰根本就不知道部落究竟是如何分布的。 不過好消息是,聰聰得到了一份荒島的地圖。地圖上標註了N個野人居住的地點(可以看作是平面上的坐標)。我們知道,同一個部落的野人總是生活在附近。我們把兩個部落的距離,定義為部落中距離最近的那兩個居住點的距離。聰聰還獲得了一個有意義的信息——這些野人總共被分為了K個部落!這真是個好消息。聰聰希望從這些信息裏挖掘出所有部落的詳細信息。他正在嘗試這樣一種算法: 對於任意一種部落劃分的方法,都能夠求出兩個部落之間的距離,聰聰希望求出一種部落劃分的方法,使靠得最近的兩個部落盡可能遠離。 例如,下面的左圖表示了一個好的劃分,而右圖則不是。請你編程幫助聰聰解決這個難題。 技術分享

Input

第一行包含兩個整數N和K(1< = N < = 1000,1< K < = N),分別代表了野人居住點的數量和部落的數量。 接下來N行,每行包含兩個正整數x,y,描述了一個居住點的坐標(0 < =x, y < =10000)

Output

輸出一行,為最優劃分時,最近的兩個部落的距離,精確到小數點後兩位。

Sample Input

4 2
0 0
0 1
1 1
1 0


Sample Output

1.00

HINT

Source

JSOI2010第二輪Contest1

思路:最小生成樹水題。

錯因:排序方向錯誤。

吐槽:最後的排序排反了,錯失90分~~~~(>_<)~~~~ ,簡直了(╯‵□′)╯︵┻━┻

#include<iostream>
#include<cmath>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define MAXN 1000001
using namespace std;
struct nond{
    int x,y;
    double z;
}edge[MAXN];
double
num[MAXN]; int n,k,tot,tot1,x[MAXN],y[MAXN],fa[MAXN]; int cmp(nond a,nond b){ return a.z<b.z; } int cmp1(double x,double y){ return x>y; } int find(int x){ if(fa[x]==x) return x; else return fa[x]=find(fa[x]); } int main(){ //freopen("people.in","r",stdin); //freopen("people.out","w",stdout); scanf("%d%d",&n,&k); for(int i=1;i<=n;i++) cin>>x[i]>>y[i]; for(int i=1;i<=n;i++) fa[i]=i; for(int i=1;i<=n;i++) for(int j=i+1;j<=n;j++){ edge[++tot].x=i; edge[tot].y=j; edge[tot].z=sqrt((x[i]-x[j])*(x[i]-x[j])+(y[i]-y[j])*(y[i]-y[j])); } sort(edge+1,edge+1+tot,cmp); for(int i=1;i<=tot;i++){ int dx=find(edge[i].x); int dy=find(edge[i].y); if(dx==dy) continue; fa[dx]=dy; num[++tot1]=edge[i].z; if(tot1==tot-1) break; } sort(num+1,num+1+tot1,cmp1); printf("%.2lf",num[k-1]); }

洛谷 1821: [JSOI2010]Group 部落劃分 Group