hdu1007 平面最近点对
挺那啥的......方法挺费解,不过速度还不错,整体就是先横向筛一遍,在纵向筛一遍,最后递归一直求求求。。。。。。
#include <cstdio>
#include <iostream>
#include <cmath>
#include <cstring>
#include <cstdlib>
#include <algorithm>
#define MAXN 100005
using namespace std;
struct Point{
double x,y;
Point(){}
Point(double _x,double _y):x(_x),y(_y){}
void input(){
scanf("%lf%lf",&x,&y);
}
};
struct Point point[MAXN],px[MAXN],py[MAXN];
double get_dis(Point p1,Point p2){
return sqrt((p1.x-p2.x)*(p1.x-p2.x)+(p1.y-p2.y)*(p1.y-p2.y));
}
bool cmpx(Point p1,Point p2) {return p1.x<p2.x;}
bool cmpy(Point p1,Point p2) {return p1.y<p2.y;}
double ffcloest(int s,int e){
if (e==s+1)
return get_dis(px[s],px[e]);
if (e==s+2)
return min(min(get_dis(px[s],px[e]),get_dis(px[s+1],px[e])),get_dis(px[s],px[s+1]));
int mid=(s+e)>>1,cnt=0;
double ans=min(ffcloest(s,mid),ffcloest(mid+1,e));
for (int i=s;i<=e;i++){
if (abs(px[i].x-px[mid].x)<=ans)
py[cnt++]=px[i];
}
//初筛完成
sort(py,py+cnt,cmpy);
for(int i=0;i<cnt;i++){
for(int j=i+1;j<cnt;j++){
if(py[j].y-py[i].y>=ans)
break;
ans=min(ans,get_dis(py[i],py[j]));
}
}
return ans;
}
int main()
{
int n;
while (scanf ("%d",&n)!=EOF){
if (!n) break;
for (int i=0;i<n;i++){
point[i].input();
px[i]=point[i];
}
sort(px,px+n,cmpx);
double dis=ffcloest(0,n-1);
printf ("%.2f\n",dis/2.0);
}
return 0;
}