HDU 5515 Game of Flying Circus 二分

来源:互联网 发布:微信站街用什么软件 编辑:程序博客网 时间:2024/06/13 05:17

题意:两个人绕四边形顺时针跑,速度v1 v2,谁先跑到一个角落得一分 ,一个人速度快,另一个能打 , 如果相遇 能打 打 另一个得一分 ,问能打的人到终点能赢吗?

思路: 二分相遇的时间,然后在算出他们在相遇的地方(如果能相遇)   然后根据情况算出相应的得分,就可以了 

代码:

#include <iostream>#include <cstdio>#include <cmath>using namespace std;const double eps=1e-5;double v1,v2,t;double le(double x,double y){    return sqrt(x*x+y*y);}void solve(){    double l=300.0/v2,r=1200.0/v2;    double ll,rr,x;//ll 原点到相遇地点 rr相遇地点到第二个角落 x跑得快的人走的路程    int flag;// 路过几个角落    int f1=0,f2=0;//分数    while (r-l>1e-8) {        double mid=(l+r)/2;        x=mid*v2;        if(300.0<=x&&600.0>x){            f2=1;f1=1;flag=1;            ll=le(x-300.0,300.0);            rr=x-300.0;        }        else if(600.0<=x&&900.0>x){            if(fabs(x-600.0)<=eps)                f2=1,f1=2;            else                f2=2,f1=1;            flag=2;            ll=le(900.0-x,300.0);            rr=le(x-600.0,300.0);        }        else{            flag=3;            ll=le(0,1200.0-x); //路过3个角落 必输        }        if((mid*v1-ll)>=0)            r=mid;        else            l=mid;    }    if(x+eps>=900.0){        f2=4;        f1=0;    }    rr-=t*v1;    if(rr<eps){        rr=300.0-rr;        if (rr>x) {            double tt=(rr-x)/(v2-v1);   // rr+tt*v1=x+tt*v2            rr+=tt*v1;        }        int c=min(4,(int)(rr/300+eps));        if (c>flag)            f1+=c-flag;        f2+=4-c;    }    else        f2+=4-flag;    if(f1>f2)        puts("Yes");    else        puts("No");}int main(int argc, const char * argv[]) {  //  freopen("/Users/yiqieshunqiziran/Desktop/ii.data.text", "r",stdin);  //  freopen("/Users/yiqieshunqiziran/Desktop/out1.data.text","w", stdout);    //init();    int T;    cin>>T;    for (int ca=1; ca<=T; ++ca) {               printf("Case #%d: ",ca);        scanf("%lf%lf%lf",&t,&v1,&v2);        if (fabs(v1-v2)<=eps)            puts("Yes");        else            solve();    }    return 0;}