zoukankan      html  css  js  c++  java
  • 计算几何入门

    艰难入门ing

    感觉我这样的去写计算几何光调bug就得5小时 

    参考资料(很多):

    OI WIki

    向量

    另一个入门blog

    检查线段相交

    板子主要是抄的KS

    POJ1127 Jack Straws

    先用向量判交,然后传递闭包

    #include <cstdio>
    #include <cstring>
    #include <cmath>
    #include <algorithm>
    #include <vector>
    using namespace std;
    typedef double db;
    
    namespace Geo {
        const db eps = 1e-8;
        const db Pi = acos(-1);
    
        inline int sgn(db x) {
            if (x < -eps) return -1;
            else if (x > eps) return 1;
            else return 0;
        } 
    
        struct Vector {
            db x, y;
    
            Vector(db x = 0, db y = 0) : x(x), y(y) {}
    
            inline friend Vector operator + (Vector u, Vector v) {
                return Vector(u.x + v.x, u.y + v.y);
            } 
    
            inline friend Vector operator - (Vector u, Vector v) {
                return Vector(u.x - v.x, u.y - v.y);
            } 
    
            inline friend Vector operator * (Vector u, Vector v) {
                return Vector(u.x * v.x, u.y * v.y);
            } 
    
            inline friend Vector operator / (Vector u, Vector v) {
                return Vector(u.x / v.x, u.y / v.y);
            } 
    
            inline friend bool operator == (Vector u, Vector v) {
                return sgn(u.x - v.x) == 0 && sgn(u.y - v.y) == 0;
            } 
    
        };
        typedef Vector Point;
        typedef vector <Point> Polygon;
    
        inline db dot(Vector u, Vector v) {
            return u.x * v.x + u.y * v.y;
        }
    
        inline db crs(Vector u, Vector v) {
            return u.x * v.y - u.y * v.x;
        }
    
        inline db length(Vector u) {
            return max(0.0, sqrt(dot(u, u)));
        }
    
        inline db angle(Vector u, Vector v) {
            return acos(dot(u, v) / length(u) / length(v));
        }
    
        inline Vector rotate(Vector u, db rad) {
            return Vector(u.x * cos(rad) - u.y * sin(rad), u.x * sin(rad) + u.y * cos(rad));
        }
    
        struct Line {
            Point p;
            Vector v;
            Line(Point p = Point(), Vector v = Vector()) : p(p), v(v) {} 
        };
    
        struct Ray : public Line {
            Ray(Point p = Point(), Vector v = Vector()) : Line(p, v) {}
        };
    
        struct Segment {
            Point a, b;
            Segment(Point a = Point(0, 0), Point b = Point(0, 0)) : a(a), b(b) {}
        };
    
        inline bool isCrs(Segment u, Segment v) {
            Point p1 = u.a, p2 = u.b, q1 = v.a, q2 = v.b;
            if (min(p1.x, p2.x) <= max(q1.x, q2.x) && min(q1.x, q2.x) <= max(p1.x, p2.x) 
                && min(p1.y, p2.y) <= max(q1.y, q2.y) && min(q1.y, q2.y) <= max(p1.y, p2.y)) {
                    //puts("in");
                    if (sgn(crs(q1 - p1, p2 - p1) * crs(q2 - p1, p2 - p1)) > 0) return 0;
                    //puts("1");
                    if (sgn(crs(p1 - q1, q2 - q1) * crs(p2 - q1, q2 - q1)) > 0) return 0;
                    //puts("2");
                    return 1;
            } else return 0;
        }
    
    } using namespace Geo;
    
    const int N = 20;
    
    int n;
    Segment s[N];
    bool f[N][N];
    
    int main() {
        #ifndef ONLINE_JUDGE
            freopen("sample.in", "r", stdin);
        #endif
    
        for (; scanf("%d", &n); getchar()) {
            if (n == 0) break;
            for (int i = 1; i <= n; i++) {
                int x1, y1, x2, y2;
                scanf("%d%d%d%d", &x1, &y1, &x2, &y2);
    //          printf("%f %f %f %f
    ", Point(x1, y1).x, Point(x1, y1).y, Point(x2, y2).x, Point(x2, y2).y);
                s[i] = Segment(Point(x1, y1), Point(x2, y2));
            }
    
            for (int i = 1; i <= n; i++)
                for (int j = 1; j <= n; j++)
                    if (isCrs(s[i], s[j])) f[i][j] = 1;
                    else f[i][j] = 0;
            
            for (int k = 1; k <= n; k++)
                for (int i = 1; i <= n; i++)
                    for (int j = 1; j <= n; j++)
                        f[i][j] |= f[i][k] & f[k][j];
    
    /*        for (int i = 1; i <= n; i++)
                printf("%f %f %f %f
    ", s[i].a.x, s[i].a.y, s[i].b.x, s[i].b.y);      */
    
            for (int u, v; ; ) {
                scanf("%d%d", &u, &v);
                if (u == 0 && v == 0) break;
                if (f[u][v]) puts("CONNECTED");
                else puts("NOT CONNECTED");
            }
        }
        return 0;
    }
    View Code

    占坑

  • 相关阅读:
    C/C++ 数据精确度的设置
    Java 接口回调
    ListView + ArrayAdapter + 接口回调
    C/C++内存详解
    第九届蓝桥杯明码
    2018蓝桥杯省赛(C/C++ C组)
    2015蓝桥杯五星填数(C++C组)
    java ee 面试时的机试题
    让div中的table居中
    javascript 调试技巧
  • 原文地址:https://www.cnblogs.com/CzxingcHen/p/13781706.html
Copyright © 2011-2022 走看看