POJ 2187 Beauty Contest( 凸包求最远点对 )


**链接:****传送门 **

题意:给出 n 个点,求出这 n 个点中最远的两个点距离的平方

思路:最远点对一定会在凸包的顶点上,然后直接暴力找一下凸包顶点中距离最远的两个点


/*************************************************************************
    > File Name: poj2187.cpp
    > Author:    WArobot 
    > Blog:      http://www.cnblogs.com/WArobot/ 
    > Created Time: 2017年05月08日 星期一 14时30分43秒
 ************************************************************************/

#include<iostream>
#include<cmath>
#include<cstdio>
#include<algorithm>
using namespace std;

#define eps 1e-10
const int maxn = 50010;
struct point{ double x,y; };

double multi(point sp,point ep,point op){
	return (sp.x-op.x)*(ep.y-op.y) >= (sp.y-op.y)*(ep.x-op.x);
}
bool operator < (const point &a,const point &b){
	return a.y < b.y || ( a.y == b.y && a.x < b.x );
}
int Graham(point pnt[] , int n , point res[]){
	int i , len , k = 0 , top = 1;
	sort(pnt,pnt+n);
	if( n == 0 ) return 0;	res[0] = pnt[0];
	if( n == 1 ) return 1;	res[1] = pnt[1];
	if( n == 2 ) return 2;	res[2] = pnt[2];
	for(int i = 2 ; i < n ; i++){
		while( top && multi( pnt[i] , res[top] , res[top-1] ))
			top--;
		res[++top] = pnt[i];
	}
	len = top;	res[++top] = pnt[n-2];
	for(int i = n - 3 ; i >= 0 ; i--){
		while( top!=len && multi( pnt[i] , res[top] , res[top-1] ))
			top--;
		res[++top] = pnt[i];
	}
	return top;
}
int Dist(point a,point b){
	return (a.x-b.x)*(a.x-b.x) + (a.y-b.y)*(a.y-b.y);
}
int main(){
	int n;
	while(~scanf("%d",&n)){
		point pnt[maxn] , res[maxn];
		for(int i = 0 ; i < n ; i++)	scanf("%lf%lf",&pnt[i].x,&pnt[i].y);
		int num = Graham( pnt , n , res );
		int dis = 0;
		for(int i = 0 ; i < num ; i++){
			for(int j = i+1 ; j < num ; j++){
				dis = max( dis , Dist( res[i] , res[j] ) );
			}
		}
		printf("%d\n",dis);
	}
	return 0;
}
posted @ 2017-05-08 14:57  ojnQ  阅读(171)  评论(0编辑  收藏  举报