Stealing a Cake [函数方程符合凸性 三分]

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4454

#pragma comment (linker,"/stack:102400000,102400000")
#include <stdio.h>
#include <map>
#include <vector>
#include <stack>
#include <queue>
#include <string.h>
#include <algorithm>
#include <string>
#include <stdlib.h>
#include <iostream>
#include <math.h>

using namespace std;

const int MM = 1111;
#define inf 0x3f3f3f3f
#define pi acos(-1.0)
const double eps = 0.000001;
typedef long long ll;
struct pos {
    double x,y,r;
};
pos ss;
pos circle;
pos rctl, rctr;
void swap(double&x,double&y) {
    double aa;
    aa=x; x=y; y=aa;
}
double sqr(double x) {return x*x;}
double dist(pos a,pos b) {
    return sqr(a.x-b.x)+sqr(a.y-b.y);
}
double f_min(double x,double y) {
    if(x>y) return y;
    else return x;
}
double f_abs(double x) {
    if(x>0) return x;
    else return -x;
}
double ans;
pos r1,r4;
pos then;
double calc(pos tt) {
    if(tt.x<=rctl.x) {
        if(tt.y>=rctr.y) return dist(r1,tt);
        else if(tt.y<=rctl.y) return dist(tt,rctl);
        else return sqr(rctl.x-tt.x);
    }
    else if(tt.x>=rctr.x) {
        if(tt.y>=rctr.y) return dist(rctr,tt);
        else if(tt.y<=rctl.y) return dist(tt,r4);
        else return sqr(tt.x-rctr.x);
    }
    else {
        if(tt.y>=rctr.y) return sqr(tt.y-rctr.y);
        else return sqr(rctl.y-tt.y);
    }
}
bool ff=true;
double gao(pos tt) {
    double sum=0.0;
    sum=sum+((double)sqrt((double)dist(ss,tt)));
    sum=sum+((double)sqrt((double)calc(tt)));  
    return sum;
}
void three(double l,double r,double op) {
    double mid, midmid, t1, t2;
    pos tt, tmp;
    while(l+eps<r) {
            mid=(l+r)/2.0;
            midmid=(mid+r)/2.0;
            t1=mid;
            t2=sqr(circle.r)-sqr(t1-circle.x);
            t2=(double)sqrt((double)t2);
            tt.x=t1; tt.y=circle.y+op*t2;
            //printf("%.2lf %.2lf\n",tt.x,tt.y);
            t1=midmid;
            t2=sqr(circle.r)-sqr(t1-circle.x);
            t2=(double)sqrt((double)t2);
            tmp.x=t1; tmp.y=circle.y+op*t2;
            if(gao(tt)>=gao(tmp)) l=mid;
            else r=midmid;
        }
        t1=l;
        t2=sqr(circle.r)-sqr(t1-circle.x);
        t2=(double)sqrt((double)t2);
        tt.x=t1; tt.y=circle.y+op*t2;
        ans=f_min(ans,gao(tt));
}
int main() {
    int i,j,k;
    while(scanf("%lf%lf",&ss.x,&ss.y)!=EOF) {
        if(ss.x==0 && ss.y==0) break;
        scanf("%lf%lf%lf",&circle.x,&circle.y,&circle.r);
        scanf("%lf%lf%lf%lf",&rctl.x,&rctl.y,&rctr.x,&rctr.y);
        if(rctl.x>rctr.x) swap(rctl.x,rctr.x);
        if(rctl.y>rctr.y) swap(rctl.y,rctr.y);
        
        r1.x=rctl.x; r1.y=rctr.y;
        r4.x=rctr.x; r4.y=rctl.y;
        double xx=circle.x-circle.r, yy=circle.x+circle.r;
        int x=xx*50, y=yy*50,m;
        pos tt;
        ans=1000000000000000.0;
        three(xx,circle.r,1);
        three(xx,circle.r,-1);
        three(circle.r,yy,1);
        three(circle.r,yy,-1);
        printf("%.2lf\n", ans);
    }
    return 0;
}
View Code

 

posted @ 2013-10-28 13:00  zhang1107  阅读(277)  评论(0编辑  收藏  举报