https://www.luogu.com.cn/paste/vfoq896a (输入输出)
code
#include <cstdio>
#include <algorithm>
#include <cmath>
const int maxn = 2e5;
int n, len, tb[maxn + 10];
struct pt {
double x, y;
} a[maxn + 10], b[maxn + 10], c[maxn + 10];
inline int cmp(const pt &a, const pt &b) {
if (a.x != b.x) return a.x < b.x;
return a.y < b.y;
}
// min
inline int cmpp(const pt &a, const pt &b) {
if (a.y != b.y) return a.y < b.y;
return a.x < b.x;
}
inline double ll(int i, int j) {
return (c[j].y - c[i].y) * (c[j].y - c[i].y) + (c[j].x - c[i].x) * (c[j].x - c[i].x);
}
double work(int l, int r) {
double d = 2e18;
if (l == r) return b[l] = a[l], d;
int mid = l + r >> 1;
d = std :: min(work(l, mid), work(mid + 1, r));
int i = l, j = mid + 1, k = l;
while (i <= mid && j <= r)
c[k++] = cmpp(b[i], b[j]) ? b[i++] : b[j++];
while (i <= mid)
c[k++] = b[i++];
while (j <= r)
c[k++] = b[j++];
for (i = l; i <= r; i++)
b[i] = c[i];
len = 0;
for (i = l; i <= r; i++)
if ((b[i].x - a[mid].x) * (b[i].x - a[mid].x) < d)
c[++len] = b[i];
for (i = 1; i < len; i++)
for (j = i + 1; (c[j].y - c[i].y) * (c[j].y - c[i].y) < d && j <= len; j++)
d = std :: min(d, ll(i, j));
return d;
}
// max
inline double k(int i, int j) {
return (a[i].y - a[j].y) / (a[i].x - a[j].x);
}
inline double L(int i, int j) {
i = tb[i], j = tb[j];
return (a[j].y - a[i].y) * (a[j].y - a[i].y) + (a[j].x - a[i].x) * (a[j].x - a[i].x);
}
inline double LL(int i, int j) {
int ii = i % len + 1;
ii = tb[ii], i = tb[i], j = tb[j];
return ((a[ii].y - a[i].y) * a[j].x + (a[i].x - a[ii].x) * a[j].y + a[i].y * a[ii].x - a[i].x * a[ii].y) * ((a[ii].y - a[i].y) * a[j].x + (a[i].x - a[ii].x) * a[j].y + a[i].y * a[ii].x - a[i].x * a[ii].y) / ((a[ii].y - a[i].y) * (a[ii].y - a[i].y) + (a[ii].x - a[i].x) * (a[ii].x - a[i].x));
}
int main(void) {
//freopen("in.in", "r", stdin);
//freopen("out.out", "w", stdout);
scanf("%d", &n);
for (int i = 1; i <= n; i++)
scanf("%lf %lf", &a[i].x, &a[i].y);
std :: sort(a + 1, a + n + 1, cmp);
// min
printf("%.2lf ", sqrt(work(1, n)));
// max
double ans = 0;
tb[len = 1] = 1;
for (int i = 2, las = 1; i <= n; i++) {
while (i <= n && a[i].x == a[las].x) i++;
if (i > n) break;
while (len > 1 && k(tb[len], i) > k(tb[len - 1], i)) len--;
las = tb[++len] = i;
}
if (tb[len] != n) tb[++len] = n;
int down = len;
for (int i = n - 1, las = n; i; i--) {
while (i && a[i].x == a[las].x) i--;
if (i < 2) break;
while (len > down && k(tb[len], i) < k(tb[len - 1], i)) len--;
las = tb[++len] = i;
}
int l = 1, r = 2;
while (l <= len) {
while (LL(r % len + 1, l) >= LL(r, l)) r = r % len + 1;
ans = std :: max(ans, std :: max(L(l, r), L(l, r + 1)));
l++;
}
printf("%.2lf\n", sqrt(ans));
return 0;
}