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 C++14 (GCC 5.4.1) (judge verdict: Accepted)

#include <bits/stdc++.h>
using namespace std;

#define eps 1e-9
#define PI acos(-1)

template<typename p_type>
struct Point {
	p_type x, y;
	Point(p_type _x = -1, p_type _y = -1) : x(_x), y(_y) {}
};

template<typename v_type>
struct Vec {
	v_type x, y;
	
	Vec(v_type _x = -1, v_type _y = -1) : x(_x), y(_y) {}
	Vec(Point<v_type> a, Point<v_type> b) {
		x = b.x - a.x;
		y = b.y - a.y;
	}
	
	Vec operator +(const Vec& rhs) const { return Vec(x + rhs.x, y + rhs.y); }
	Vec operator -(const Vec& rhs) const { return Vec(x - rhs.x, y - rhs.y); }
	
	Vec& scale(v_type s) { return *this = Vec(x * s, y * s); }
	Vec& rot(double theta) {
		v_type new_x = x * cos(theta) - y * sin(theta);
		v_type new_y = x * sin(theta) + y * cos(theta);
		return *this = Vec(new_x, new_y);
	}
	
	v_type dot(const Vec& rhs) const { return x * rhs.x + y * rhs.y; }
	v_type cross(const Vec& rhs) const { return x * rhs.y - y * rhs.x; }
	double mag() const { return sqrt(x*x + y*y); }
};

using P = Point<double>;
using V = Vec<double>;

double dist(P a, P b) {
	return sqrt((a.x-b.x)*(a.x-b.x) + (a.y-b.y)*(a.y-b.y));
}

struct Circle {
	P center;
	double r;
	Circle(P _center, double _r) : center(_center), r(_r) {}
};

// returns true if c1 and c2 intersect, their points of intersection stored in ans
bool intersect(Circle c1, Circle c2, vector<P>& ans) {
	P p = c1.center, q = c2.center;
	double r1 = c1.r, r2 = c2.r;
	double d = dist(p, q);
	if(d > r1 + r2 || d < fabs(r1 - r2)) return false;
	
	double a = (r1*r1 - r2*r2 + d*d) / (2*d);
	double h = sqrt(r1 * r1 - a * a);

	V u(p, q), v(p, q);
	u.scale(h/u.mag());
	u.rot(PI/2);
	v.scale(a/v.mag());

	ans.push_back(P(p.x + u.x + v.x, p.y + u.y + v.y));
	u.rot(PI);
	ans.push_back(P(p.x + u.x + v.x, p.y + u.y + v.y));
	return true;
};

int main() {
	ios_base::sync_with_stdio(false);
	cin.tie(0);
	
	int n;
	cin >> n;
	vector<P> points(n);
	for(P& p : points) {
		cin >> p.x >> p.y;
	}
	
	double lo = 0, hi = 2000;
	double mid;
	for(int rep = 0; rep < 100; rep++) {
		mid = lo + (hi - lo)/2;
		bool ok = false;
		
		for(int i = 0; i < n; i++) {
			for(int j = i+1; j < n; j++) {
				Circle c1(points[i], mid), c2(points[j], mid);
				vector<P> ans;
				if(intersect(c1, c2, ans)) {
					for(P p : ans) {
						bool now = true;
						for(int k = 0; k < n; k++) {
							if(dist(p, points[k]) > mid + eps) {
								now = false;
							}
							
						}
						
						ok = ok || now;
					}
				} 
			}
		}

		if(ok) {
			hi = mid;
		} else {
			lo = mid;
		}
	}
	
	cout << fixed << setprecision(10) << mid << endl;
}