hdu6097[二分+解析几何] 2017多校6

/*hdu6097[二分+解析几何] 2017多校6*/
#include <bits/stdc++.h>
using namespace std;
const double eps=1e-9;
struct node{
    double x,y;
    node(double X=0.0,double Y=0.0):
    x(X),y(Y){}
}p,q;
double dist(node a,node b){
    return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));
}
int T;
double A,B,C,a,b,c,h,R;
bool check(){
    a=sqrt(b*b+c*c);
    A=c*c;
    B=-2.0*a*a*h;
    C=a*a*h*h-a*a*b*b+b*b*R*R;
    double delta=B*B-4.0*A*C;
    //cout<<"delta: "<<delta<<endl;
    if(delta>=0.0){//判断复根    
        double yy1=0.5*(-B+sqrt(delta))/A;
        double yy2=0.5*(-B-sqrt(delta))/A;
        if(R*R-yy1*yy1>=0.0||R*R-yy2*yy2>=0.0)
            return true;    
        else return false;
    }
    else return false;
}
void solve(){
    double t1,t2;
    t1=(p.x+q.x)*0.5;
    t2=(p.y+q.y)*0.5;
    h=dist(node(t1,t2),node());
    c=0.5*dist(p,q);
    double l=0,r=R-h;
    for(int i=0;i<35;i++){
        b=(l+r)*0.5;
        if(check()){
            r=b;
        }
        else{
            l=b;
        }
    }
    b=(l+r)*0.5;
    printf("%.8f
",2.0*sqrt(b*b+c*c));
    /*....*/
}
int main(){
    //freopen("1002.in","r",stdin);
    //freopen("out.out","w",stdout);
    scanf("%d",&T);
    while(T--){
        scanf("%lf",&R);
        scanf("%lf%lf",&p.x,&p.y);
        scanf("%lf%lf",&q.x,&q.y);
        solve();
    }
    return 0;
}

比赛的时候忘记判断复根了!!  QAQ

原文地址:https://www.cnblogs.com/UnderSilenceee/p/7346668.html