请参考先修班第十四次课课件(与 题解.pdf
有冲突,请以此处为准)
#include <bits/stdc++.h>
using namespace std;
typedef double db;
#define cp const point &
#define eps 1e-10
struct point
{
db x, y;
point(db a = 0, db b = 0) : x(a), y(b) {}
point operator+(cp r) const { return point(x + r.x, y + r.y); }
point operator-(cp r) const { return point(x - r.x, y - r.y); }
point operator*(db r) const { return point(x * r, y * r); }
point operator/(db r) const { return point(x / r, y / r); }
db abs() const { return hypot(x, y); }
db norm() const { return x * x + y * y; }
void get() { scanf("%lf%lf", &x, &y); }
} a, b, c, d;
db dot(cp a, cp b) { return a.x * b.x + a.y * b.y; }
db cross(cp a, cp b) { return a.x * b.y - a.y * b.x; }
int f(cp a, cp b)
{
if (cross(a, b) > eps)
{
return 1; //逆时针
}
if (cross(a, b) < -eps)
{
return -1; //顺时针
}
if (dot(a, b) < -eps)
{
return 2; // P在AB左方
}
if (a.norm() < b.norm() + eps)
{
return -2; // P在AB右方
}
return 0; // P在AB内部
}
bool isIntersect(cp a, cp b, cp c, cp d)
{
return f(b - a, c - a) * f(b - a, d - a) <= 0 && f(d - c, a - c) * f(d - c, b - c) <= 0;
}
point intersect(cp a, cp b, cp c, cp d)
{
return c + (d - c) * (cross(a - c, b - a) / cross(d - c, b - a));
}
db dis_sp(cp a, cp b, cp p)
{
if (dot(b - a, p - a) < 0)
{
return (p - a).abs();
}
if (dot(a - b, p - b) < 0)
{
return (p - b).abs();
}
return abs(cross(b - a, p - a)) / (b - a).abs();
}
signed main()
{
a.get(), b.get(), c.get(), d.get();
if (isIntersect(a, b, c, d))
{
if (abs(abs(dot(b - a, d - c)) - (b - a).abs() * (d - c).abs()) < eps)
{
printf("perfect");
}
else
{
point r = intersect(a, b, c, d);
printf("yes\n%lf %lf", r.x, r.y);
}
}
else
{
db r = min(min(dis_sp(a, b, c), dis_sp(a, b, d)), min(dis_sp(c, d, a), dis_sp(c, d, b)));
printf("no\n%lf", r);
}
return 0;
}