二分法,对y轴归并排序。
#include <iostream>
#include<string>
#include<cmath>
#include<iomanip>
#include<vector>
#include<limits.h>
#include<algorithm>
using namespace std;
const int num = 400010;
struct node {
long long x, y;
}poi[num];
int n;
int may[num];
bool cmp1(node a, node b) {
return a.x < b.x;
}
bool cmp2(node a, node b) {
return a.y<b.y;
}
long long dis(node a, node b) {
return (a.x - b.x) * (a.x - b.x) + (a.y - b.y) * (a.y - b.y);
}
long long solve(int l, int r) {
if (l == r)return LLONG_MAX;
else if (l + 1 == r) {
if (poi[l].y > poi[r].y)swap(poi[l], poi[r]);
return dis(poi[l], poi[r]);
}
int mid = 1+(l + r) / 2;
long long le = solve(l, mid-1);
long long ri = solve(mid , r);
long long mi = min(le, ri);
inplace_merge(poi+l,poi+mid,poi+r+1, cmp2);
int k = 0;
for (int i = l; i <=r; i++) {
if (fabs(poi[i].x - poi[mid].x) < mi) {
may[k++] = i;
}
}
for (int i = 0; i < k; i++) {
for (int j = i + 1; j <= i + 5&&j<k; j++) {
mi = min(mi, dis(poi[may[i]], poi[may[j]]));
}
}
return mi;
}
int main()
{
cin >> n;
for (int i=0; i < n; i++)cin >> poi[i].x >> poi[i].y;
sort(poi, poi + n, cmp1);
cout<<solve(0, n - 1);
}