UVA 1476

来源:互联网 发布:物流单号查询软件 编辑:程序博客网 时间:2024/06/11 00:36
 题目意思:

 给你n(n<=10000)个抛物线,第i个抛物线的方程为fi(x) = ai*x*x + bi*x + c; (a>=0&&a<=100&&|b|<=5000,|c|<=5000)求x>=0&&x<=1000 内 F(x) = Max(fi(x)) 要最小.


解题思路:

首先对于每一条抛物线他们的ai>=0,所以所有的抛物线都是向上的,对于x∈[0,1000],求的是Max(fi(X)),所以我们可以将所有低于点( X,Max(fi(X) )的点都去掉,所以剩下的图形是一个凸性函数,所以我们可以根据三分法来求该凸性函数的最小值,即本题所要求的解.


原题地址:

http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&category=493&page=show_problem&problem=4222

#include <stdio.h>#include <string.h>#include <stdlib.h>#include <math.h>#define MAXN 10010#define eps  1e-12typedef struct node { double a,b,c;void read(){     scanf("%lf%lf%lf",&a,&b,&c);}};node F[MAXN];int dcmp(double x){  if(fabs(x)<eps)return 0;return x<0?-1:1;}double max(double aa,double bb){   return dcmp(aa-bb)<0?bb:aa;}double f(int i,double x){  return F[i].a*x*x+F[i].b*x+F[i].c;}double Cal(double x,int n){double MaxVal;MaxVal = f(0,x);for(int i=1;i<n;++i){MaxVal = max(f(i,x),MaxVal);}return MaxVal;}double solve(int n){     double L,R,Mid,MMid,MidVal,MMidVal;L = 0.00;R = 1000.00;while(dcmp(R-L)==1){        Mid  = (R+L)/2;MMid = (Mid+R)/2;        MidVal = Cal(Mid,n);MMidVal = Cal(MMid,n);if(dcmp(MidVal-MMidVal)==1){             L = Mid;}else R = MMid;}return Cal(L,n);}int main(){    int n;   int T,i;   scanf("%d",&T);   while(T--){      scanf("%d",&n);  for(i=0;i<n;++i){  F[i].read();  }  double ans = solve(n);  printf("%.4lf\n",ans);   }   return 0;}


  



0 0
原创粉丝点击