题目大意:一个马戏团要建一个锥形的帐篷,要求用最小的体积把给出的点包在里面,问最小的高度跟半径是多少。
思路:把立体几何转化为平面几何,把所有的点到z轴的距离当作横坐标,把点的z坐标当作纵坐标放到平面坐标系里,然后找出一条满足要求的线即可。用三分法找出高度,然后求半径。开始精度没有设置好WA了一次
代码如下:
#include<iostream>
#include<cstdio>
#include<cmath>
using namespace std;
struct Point{
double x,y;
};
Point dot[10005];
int n;
double getr(double h){
double r=0;
for(int i=0;i<n;++i){
double tmp=h*dot[i].x/(h-dot[i].y);
if(r<tmp)r=tmp;
}
return r;
}
int main(){
// freopen("data.txt","r",stdin);
int T;
scanf("%d",&T);
while(T--){
scanf("%d",&n);
double R=0;
double L=1e7;
for(int i=0;i<n;++i){
double a,b,c;
scanf("%lf%lf%lf",&a,&b,&c);
dot[i].x=sqrt(a*a+b*b);
dot[i].y=c;
if(c>R)R=c;
// cout<<i<<' '<<R<<endl;
}
// cout<<R<<' '<<L<<endl;
while(L-R>1e-6){
double mid=(R+L)/2;
double midmid=(mid+L)/2;
double rmid=getr(mid);
double rmidmid=getr(midmid);
double vmid=rmid*rmid*mid;
double vmidmid=rmidmid*rmidmid*midmid;
if(vmid<vmidmid){
L=midmid;
}
else R=mid;
// cout<<R<<' '<<L<<endl;
}
double r=getr(L);
printf("%.3lf %.3lf\n",L,r);
}
return 0;
}