题目描述
给定平面上 n 个点,找出其中的一对点的距离,使得在这 n个点的所有点对中,该距离为所有点对中最小的。
输入
第一行:n ,保证 2≤n≤200000 。
接下来 n 行:每行两个实数:x ,y 表示一个点的行坐标和列坐标,中间用一个空格隔开
输出
仅一行,一个实数,表示最短距离,精确到小数点后面 4 位。
AC代码
#include <iostream>
#include <cstdio>
#include <cmath>
#include <cstring>
#include <algorithm>
using namespace std;
const int N=1e4+10;
typedef long long LL;
struct node
{
double x,y;
}p[N];
int temp[N];
bool cmp(const node &a,const node &b)
{
if(a.x==b.x)
return a.y<b.y;
else
return a.x<b.x;
}
bool cmp2(const int &a,const int &b)
{
return p[a].y<p[b].y;
}
double dis(int i,int j)
{
return sqrt((p[i].x-p[j].x)*(p[i].x-p[j].x)+(p[i].y-p[j].y)*(p[i].y-p[j].y));
}
double merge(int l,int r)
{
double res=0x3f3f3f3f;
if(l>=r)
return res;
int mid=l+r>>1;
res=min(merge(l,mid),merge(mid+1,r));
int k=0;
for(int i=l;i<=r;i++)
{
if(fabs(p[mid].x-p[i].x)<res)
{
temp[k++]=i;
}
sort(temp,temp+k,cmp2);
for(int i=0;i<k;i++)
{
for(int j=i+1;j<k;j++)
{
if(fabs(p[temp[j]].y-p[temp[i]].y)<res)
res=min(res,dis(temp[j],temp[i]));
}
}
}
return res;
}
int main()
{
int n;
cin>>n;
for(int i=0;i<n;i++)
{
double x,y;
cin>>x>>y;
p[i].x=x;
p[i].y=y;
}
sort(p,p+n,cmp);
printf("%.4lf\n",merge(0,n-1));
}
运行结果
(电脑截图坏了,请谅解)
宋江,卢俊义,吴用,公孙胜,关胜,林冲,秦明,呼延灼,花荣,柴进,李应,朱仝,鲁智深,武松,董平,张清,杨志,徐宁,索超,戴宗,刘唐,李逵,史进,穆弘,雷横,李俊,阮小二,张横,阮小五,张顺,阮小七,杨雄,石秀,解珍,解宝,燕青,朱武,黄信,孙立,宣赞,等108人觉得很赞。您确定不来一个吗?