Problem:
Score : 600 points

Problem Statement

Given are N points (x_i, y_i) in a two-dimensional plane.

Find the minimum radius of a circle such that all the points are inside or on it.

Constraints

2 \leq N \leq 50

0 \leq x_i \leq 1000

0 \leq y_i \leq 1000

The given N points are all different.

The values in input are all integers.

Input

Input is given from Standard Input in the following format:

N
x_1 y_1
:
x_N y_N

Output

Print the minimum radius of a circle such that all the N points are inside or on it.

Your output will be considered correct if the absolute or relative error from our answer is at most 10^{-6}.

Sample Input 1

2
0 0
1 0

Sample Output 1

0.500000000000000000

Both points are contained in the circle centered at (0.5,0) with a radius of 0.5.

Sample Input 2

3
0 0
0 1
1 0

Sample Output 2

0.707106781186497524

Sample Input 3

10
10 9
5 9
2 0
0 0
2 7
3 3
2 5
10 0
3 7
1 9

Sample Output 3

6.726812023536805158

If the absolute or relative error from our answer is at most 10^{-6}, the output will be considered correct.

Solution in Java8 (OpenJDK 1.8.0) (judge verdict: Wrong Answer)


import java.util.Arrays;
import java.util.LinkedList;
import java.util.Scanner;

public class Main {
    int n;
    int[] x, y;
    double EPS = 1e-12;
    double D = 1e-6;
    void run() {
        Scanner sc = new Scanner(System.in);
        n = sc.nextInt();
        x = new int[n];
        y = new int[n];
        for (int i = 0; i < n; i++) {
            x[i] = sc.nextInt();
            y[i] = sc.nextInt();
        }

        double ans = 1e12;
        for (int i = 0; i < n; i++) for (int j = i + 1; j < n; j++) {
            double[] pqr = calc2(i, j);
            if (ok2(pqr)) {
                debug("2", "", Math.sqrt(pqr[2]));
                ans = Math.min(ans, Math.sqrt(pqr[2]));
            }

            for (int k = j + 1; k < n; k++) {
                double[] abc = calc(i, j, k);
                if (abc.length == 0) continue;
                if (ok(abc)) {
                    double r2 = (abc[0] * abc[0] + abc[1] * abc[1] + EPS) / 4 - abc[2] + EPS;
                    debug("3", Math.sqrt(r2));
                    ans = Math.min(ans, Math.sqrt(r2));
                }
            }
        }
        System.out.println(ans);
    }

    boolean ok(double[] abc) {
        for (int i = 0; i < n; i++) {
            double d = fn(i, abc);
            if (d > D) return false;
        }
        return true;
    }

    double fn(int idx, double[] abc) {
        return x[idx] * x[idx] + y[idx] * y[idx] + abc[0] * x[idx] + abc[1] * y[idx] + abc[2] + EPS;
    }

    double[] calc(int i, int j, int k) {
        int d = (y[i] - y[j]) * (x[i] - x[k]) - (y[i] - y[k]) * (x[i] - x[j]);
        if (d == 0) return new double[] {};
        double a = - 1.0 * ((x[i] - x[k]) * (x[i] * x[i] - x[j] * x[j] + y[i] * y[i] - y[j] * y[j] + EPS)
                - 1.0 * (x[i] - x[j]) * (x[i] * x[i] - x[k] * x[k] + y[i] * y[i] - y[k] * y[k]) + EPS) / d + EPS;
        double b = - 1.0 * ((y[i] - y[k]) * (x[i] * x[i] - x[j] * x[j] + y[i] * y[i] - y[j] * y[j] + EPS)
                - 1.0 * (y[i] - y[j]) * (x[i] * x[i] - x[k] * x[k] + y[i] * y[i] - y[k] * y[k]) + EPS) / d + EPS;
        double c = - (x[i] * x[i] + y[i] * y[i] + a * x[i] + b * y[i]) + EPS;
        return new double[]{a, b, c};
    }

    double[] calc2(int i, int j) {
        double p = 1.0 * (x[i] + x[j]) / 2 + EPS, q = 1.0 * (y[i] + y[j]) / 2 + EPS;

        double r2 = (x[i] - p) * (x[i] - p) + (y[i] - q) * (y[i] - q) + EPS;

        return new double[] {p, q, r2};
    }

    boolean ok2(double[] pqr) {
        for (int i = 0; i < n; i++) {
            double d = fn2(i, pqr);
            if (d > D) return false;
        }
        return true;
    }

    double fn2(int idx, double[] pqr) {
        return (x[idx] - pqr[0]) * (x[idx] - pqr[0]) + (y[idx] - pqr[1]) * (y[idx] - pqr[1]) - pqr[2] + EPS;
    }


    void debug(Object... os) {
        System.err.println(Arrays.deepToString(os));
    }

    public static void main(String[] args) {
        new Main().run();
    }
}