zoukankan      html  css  js  c++  java
  • 点在多边形内的判断

    判断点在多边形内

    凸多边形

    凸多边形考虑叉积,因为在凸多边形中,我们假设围绕多边形走一圈,如果点在多边形内,那么这个点一直在我们的同一侧。按照这个性质,我们顺时针或者逆时针处理多边形上的点,叉积运算,算参考的和多边形上连续的两个点,如何叉积的结果符号发生变化,那么不再多边形内。

    double det(point p1,point p2,point p0)
    {
        return (p1.x-p0.x)*(p2.y-p0.y)-(p2.x-p0.x)*(p1.y-p0.y);
    }
     
    bool isinside(point p)
    {
        double pre,now;
        for(int i=0;i<n;i++){
            now=det(p,poly[i],poly[(i+1)%n]);
            if(i>0){
                if(pre*now<0){
                    return 0;
                }
            }
            pre=now;
        }
        return true;
    }
    

    一般的多边形。

    凹多边形不满足上面的性质,使用不能使用。计算机图形学中讲授过射线与多边形的交点个数,如果为偶数,则不再多边形内,否则在多边形内。射线与多边形变重合不考虑,与顶点相交特殊考虑,不考虑或者算一个。
    这里我们作一条水平向右的射线。
    首先,对于多边形的水平边不做考虑,其次,对于多边形的顶点和射线相交的情况,如果该顶点是其所属的边上纵坐标较大的顶点,则计数,否则忽略该点。最后,对于Q在多边形上的情形,直接判断Q是否属于多边形。
    点积和叉积判断点在直线上,运用叉积判断点在多边形的哪一侧,这样判断和交点奇偶数等效,这样写较为减掉,写的时候最后手动模拟一下,验证正确性。

    ll operator^(node p1, node p2) {
        return p1.x*p2.x + p1.y*p2.y;
    }
    double det(node A, node B, node C) {
        //a×b>0 则说明 b在a的左上方
        //a×b<0 则说明b在a的右下方
        return (B.x - A.x)*(C.y - A.y) - (B.y - A.y)*(C.x - A.x);
    }
    bool onSeg(node p, node l1, node l2) {
        return  det(p, l1, l2) == 0 && ((l1 - p)^(l2 - p))<=0;
    }
    //poly点顺或者逆时针
    bool PointInPolygon(node p, vector<node>poly) {
        int cnt = 0;
        int len = poly.size();
        for (int i = 0; i < poly.size(); i++) {
            if (onSeg(p, poly[i], poly[(i + 1)%len]))return true;
            ll k = det(poly[i], poly[(i + 1) % len], p);
            ll d1 = poly[i].y - p.y;
            ll d2 = poly[(i + 1) % len].y-p.y;
            if (k > 0 && d1 <= 0 && d2 > 0)cnt++;
            if (k < 0 && d2 <= 0 && d1>0)cnt--;
        }
        if (cnt != 0)return true;
        return false;
    }
    
    不疯魔不成活
  • 相关阅读:
    struts1.2一些知识
    iText的用法
    <action里的input的作用
    CSS超链接样式常见四种状态控制
    Win7系统IIS7+Tomcat7集成
    Marquee 使用方法详解
    JAVA中String与StringBuffer的区别
    2020 8 31 每日总结
    2020 10 1
    2020 9 30
  • 原文地址:https://www.cnblogs.com/gzr2018/p/11250887.html
Copyright © 2011-2022 走看看