ZOJ - 4041 - Chasing(数学)

ZOJ - 4041 - Chasing

题意:

在 Y 轴左半边有两个人 A,B,他们的位置分别为 (XA,YA), (XB,YB)

已知 B 的速度为 A 的 k 倍

判断 B 能否在A到达 Y 轴前抓住 A

 

题解:

即判断Y轴上是否存在一点P使得 PB/PA >= k

设P为(0, YA+a)

则PA = sqrt(XA^2 + a^2) , PB = sqrt(XB^2 + (YA+a-YB)^2)

因为XA,XB < 0 ,所以PA,PB >0

将两边同乘PA,并平方去根号,得:

XB^2 + (YA+a-YB)^2 >= (XA^2 + a^2) * k^2 

令 dy = YA - YB

得 (k^2 - 1) * a^2 - 2*dy * a  + k^2 * XA^2 - XB^2 - dy^2 <= 0

当 A 与 B 在同一点时A不能逃脱

当 k > 1 时,只需要判断上述一元二次方程是否有解即可,即 b^2 - 4ac >= 0 有解,有解则A可以逃脱输出'N'

当 k = 1 且 YA != YB 时,就是一元二次方程,其必然有解

当 k = 1 且 YA == YB 时,这个时候就是判断 C <= 0是否成立,其中C为常数 = XA^2 - XB^2,成立则输出'N'

当 k < 1 时,B不能追上A

 


#include 
#include 
#include 
#include 
#include 

using namespace std;
int T;
int main()
{
    scanf("%d",&T);
    while(T--){
        double x1,x2,y1,y2,k;
        scanf("%lf%lf%lf%lf%lf",&x1,&y1,&x2,&y2,&k);
        if(x1 == x2 && y1 == y2){ // AB刚开始在同一位置,B会抓到A
            printf("Y\n");
            continue;
        }
        if(k < 1){ // 如果 B 比 A 慢,则不可能抓到 A
            printf("N\n");
            continue;
        }
        double dy = y1-y2; // AB 的竖直方向的位移
        if(k == 1 && dy == 0){
            if(x1 <= x2) printf("Y\n");
            else printf("N\n");
            continue;
        }
        double A = k*k - 1, B = 2 * dy, C = x1*x1*k*k - x2*x2 - dy*dy;
        double mi = B * B - 4 * A * C;
        if(mi >= 0) printf("N\n");
        else printf("Y\n");
    }
    return 0;
}

 

你可能感兴趣的:(几何)