poj3301 Texas Trip【三分算法】
题目地址:http://poj.org/problem?id=3301
简述:T组测试数据,每组线输入n,代表有n个点,接下来输入这n个点的坐标,坐标都是整数。
要求用一个最小的正方形覆盖所有的点,输出它的面积,精确到小数点后两位。
算法思路:枚举角度,计算面积, 三分枚举
(可参考:程序设计 解题策略 吴永辉...著 394页)
代码:
#include <stdio.h> #include <string.h> #include <stdlib.h> #include <ctype.h> #include <math.h> #include <stack> #include <queue> #include <iostream> #include <string> #include <algorithm> #define eps 1e-9 using namespace std; int tg, n; int x[1000], y[1000]; double calc(double d) { int i, j; double dis1,dis2,dis; dis=0.0; for(i=1; i<n; i++) { for(j=i+1; j<=n; j++) { dis1=fabs( cos(d)*(y[i]-y[j])-sin(d)*(x[i]-x[j]) ); dis2=fabs( sin(d)*(y[i]-y[j])+cos(d)*(x[i]-x[j]) ); if(dis < dis1 ) dis = dis1; if(dis < dis2 ) dis = dis2; } } return (dis*dis); } int main() { double ll, rr, mid, midmid; double s1, s2; cin>>tg; while(tg--) { cin>>n; for(int i=1; i<=n; i++){ cin>>x[i]>>y[i]; } ll=0.0; rr=acos(-1.0); //rr=180.0 确定好区间 while( rr-ll>=eps ) { mid = (ll+rr)/2; midmid=(rr+mid)/2; s1=calc(mid); s2=calc(midmid); if(s1<s2){ rr=midmid; }else { ll=mid; } } printf("%0.2lf\n", s1<s2?s1:s2); } return 0; }