HDU

来源:互联网 发布:windows xp硬盘安装版 编辑:程序博客网 时间:2024/06/08 17:36

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

解题思路:http://blog.csdn.net/nightmare_ak/article/details/77944442

AC代码:

#include<cstdio>#include<cmath>#include<iostream>#include<algorithm>#include<iomanip>using namespace std;const int MAXN = 100 + 5;const double PI = 3.1415926;const double EPS = 1e-10;double R;//反演圆半径struct Point{    double _x, _y;    Point(double x = 0.0, double y = 0.0) :_x(x), _y(y) {}    Point(const Point& p) { _x = p._x, _y = p._y; }    void toMove(Point a, double rad, double d)    {        _x = a._x + cos(rad)*d;        _y = a._y + sin(rad)*d;    }    Point operator+(Point a) { return Point(_x + a._x, _y + a._y); }    Point operator-(Point a) { return Point(_x - a._x, _y - a._y); }    friend Point operator*(double a, Point p) { return Point(a*p._x, a*p._y); }    friend istream& operator >> (istream& in, Point& point)    {        in >> point._x >> point._y;        return in;    }    friend ostream& operator<<(ostream& out, const Point& point)    {        out << fixed << setprecision(8) << point._x << ' ' << point._y;        return out;    }}polygon[MAXN];double getDis(double x1, double y1, double x2, double y2){    return sqrt((x1 - x2)*(x1 - x2) + (y1 - y2)*(y1 - y2));}double getDis(Point a, Point b){    return getDis(a._x, a._y, b._x, b._y);}int judgeZero(double a)//a>0为1,<0为-1,=0为0{    return (a > EPS) - (a < -EPS);}struct Circle{    Point _o;    double _r;    Circle(double x = 0.0, double y = 0.0, double r = 0.0) :_o(x, y), _r(r) {}    Circle(const Point& o, double r) :_o(o), _r(r) {}    Circle getAnti(const Point& point)    {        Circle antic;        double dis = getDis(point, _o);        double tmp = R*R / (dis*dis - _r*_r);        antic._r = tmp*_r;        antic._o._x = point._x + tmp*(_o._x - point._x);        antic._o._y = point._y + tmp*(_o._y - point._y);        return antic;    }    friend istream& operator >> (istream& in, Circle& circle)    {        in >> circle._o >> circle._r;        return in;    }    friend ostream& operator<<(ostream& out, const Circle& circle)    {        out << circle._o << ' ' << circle._r;        return out;    }};double getCross(Point p1, Point p2, Point p){    return (p1._x - p._x)*(p2._y - p._y) - (p2._x - p._x)*(p1._y - p._y);}bool toJudge1(Point p, Point a, Point b)//点p与线段ab{    if (judgeZero(getCross(a, b, p)) != 0)        return false;    if (p._x<min(a._x, b._x) || p._x>max(a._x, b._x))//trick:垂直或平行坐标轴;        return false;    if (p._y<min(a._y, b._y) || p._y>max(a._y, b._y))        return false;    return true;}bool toJudge2(Point a, Point b, Point c, Point d)//线段ab与线段cd{    if (toJudge1(c, a, b) || toJudge1(d, a, b) || toJudge1(a, c, d) || toJudge1(b, c, d))        return true;    if (judgeZero(getCross(a, b, c)*getCross(a, b, d)) < 0 && judgeZero(getCross(c, d, a)*getCross(c, d, b)) < 0)//==0的特殊情况已经在前面排除        return true;    return false;}bool toJudge3(Point p, Point a, Point b)//点p与直线ab{    return judgeZero(getCross(a, b, p)) == 0;}bool toJudge4(Point a, Point b, Point c, Point d)//直线ab与直线cd{    double x1 = a._x - b._x;    double y1 = a._y - b._y;    double x2 = c._x - d._x;    double y2 = c._y - d._y;    if (judgeZero(x1*y2 - x2*y1) != 0)        return true;    if (toJudge3(a, c, d))//两直线重合        return true;    return false;}bool toJudge5(Point a, Point b, Point c, Point d)//线段ab与直线cd{    if (judgeZero(getCross(c, d, a)*getCross(c, d, b)) <= 0)        return true;    return false;}Point getPoint(Point p1, Point p2, Point p3, Point p4)//求出交点,直线(线段)p1p2与直线(线段)p3p4{    double x1 = p1._x, y1 = p1._y;    double x2 = p2._x, y2 = p2._y;    double x3 = p3._x, y3 = p3._y;    double x4 = p4._x, y4 = p4._y;    double lamta = ((x2 - x1)*(y3 - y1) - (x3 - x1)*(y2 - y1)) / ((x4 - x1)*(y2 - y1) - (x2 - x1)*(y4 - y1));    return Point((lamta*x4 + x3) / (lamta + 1), (lamta*y4 + y3) / (lamta + 1));}bool toJudge6(Point a, int n)//点是否含于多边形{    Point b(-10000000.0 + a._x, a._y);//向左无穷远的线段    int count = 0;    for (int i = 0;i < n;++i)    {        Point c = polygon[i], d = polygon[(i + 1) % n];        if (toJudge1(a, c, d)) //如果点在线段上,那么一定在多边形内            return true;        if (judgeZero((a._x - b._x)*(c._y - d._y) - (c._x - d._x)*(a._y - b._y)) == 0)            continue;//如果边与射线平行        if (!toJudge2(a, b, c, d))            continue;//如果边与射线没有交点        Point lower;        if (c._y < d._y) lower = c;        else lower = d;        if (toJudge1(lower, a, b)) //如果纵坐标小的点与射线有交点            continue;        count++;    }    return count % 2 == 1;}int main(){    for (int n,m;scanf("%d", &n) == 1;)    {        for (int i = 0;i < n;++i)            cin >> polygon[i];        scanf("%d", &m);        for (int i = 1;i <= m;++i)        {            Point tmp;            cin >> tmp;            if (toJudge6(tmp, n))                puts("Yes");            else                puts("No");        }    }    return 0;}