Machining Disc Rotors Gym - 101955L (Computational Geometry)

Machining Disc Rotors Gym - 101955L

The meaning of problems: there is a circle \ ((0,0) \) of the great circle is \ (n-\) disjoint circular cut (the cut off of FIG shaded area). Ensure \ (n \) will not be a case of a great circle containing the entire circle. Q. After cutting diameter of the remaining portion of the great circle (polygon points most distant).

Solution: Obviously the diameter of the remaining part of one of the following two ways:

  • We had great circle of diameter.
  • Distance between the two intersections.

How to determine whether there is a diameter of it? We can each intersection point symmetrically about the center, if there is not a point of symmetry in \ (n-\) within a circle, indicating that the point symmetry with a diameter of dots is not cut off. If not, the maximum distance between two intersection.

#include <bits/stdc++.h>
#define fopi freopen("in.txt", "r", stdin)
#define fopo freopen("out.txt", "w", stdout)
using namespace std;
typedef long long LL;
const int inf = 0x3f3f3f3f;
const double eps = 1e-10;
const int maxn = 1000 + 10;

struct Point{
    double x,y;
    Point(double x=0,double y=0):x(x),y(y){}
};
typedef Point Vector;
Vector operator + (Vector A,Vector B){
    return Vector(A.x+B.x,A.y+B.y);
}
Vector operator - (Point A,Point B){
    return Vector(A.x-B.x,A.y-B.y);
}
Vector operator * (Point A,double p){
    return Vector(A.x*p,A.y*p);
}

int dcmp(double x) { return fabs(x) < eps ? 0 : (x < 0 ? -1 : 1); }
bool operator == (const Point& a,const Point& b){
    return dcmp(a.x-b.x)==0&&dcmp(a.y-b.y)==0;
}

double Dot(Vector A,Vector B){
    return A.x*B.x+A.y*B.y;
}
double Length(Vector A){
    return sqrt(Dot(A,A));
}

struct Circle{
    Point c;
    double r;
    Circle() {}
    Circle(Point c,double r):c(c),r(r){}
    Point point(double a){
        return Point(c.x+cos(a)*r,c.y+sin(a)*r);
    }
};

double angle(Vector v) {
    return atan2(v.y, v.x);
}

//Circle and Circle intersection
int CCIntersection(Circle C1,Circle C2,vector<Point>& sol){
    double d=Length(C1.c-C2.c);
    if(dcmp(d)==0){
        if(dcmp(C1.r-C2.r)==0)return -1;
        return 0;
    }
    if(dcmp(C1.r+C2.r-d)<0)return 0;
    if(dcmp(fabs(C1.r-C2.r)-d)>0)return 0;

    double a=angle(C2.c-C1.c);
    double da=acos((C1.r*C1.r+d*d-C2.r*C2.r)/(2*C1.r*d));

    Point p1=C1.point(a-da),p2=C1.point(a+da);

    sol.push_back(p1);
    if(p1==p2)return 1;
    sol.push_back(p2);
    return 2;
}

bool PinC(Point p, Circle c) { //Point in Circle
    double dist = Length(p-c.c);
    return dcmp(dist-c.r) < 0;
}


int T, n;
double r;
Circle a[maxn];
vector<Point> sect, k;

bool check() {
    if (sect.empty()) return true;
    for (auto p : sect) {
        bool flag = true;
        Point p1 = {-p.x, -p.y};
        for (int i = 1; i <= n; i++)
            if (PinC(p1, a[i])) {
                flag = false;
                break;
            }
        if (flag) return true;
    }
    return false;
 }

int main() {
    scanf("%d", &T);
    for (int ca = 1; ca <= T; ca++) {
        sect.clear();
        scanf("%d%lf", &n, &r);
        Circle mid = {{0,0}, r};
        Point p1, p2;
        for (int i = 1; i <= n; i++) {
            int x, y, z;
            scanf("%d%d%d", &x, &y, &z);
            a[i] = {{x, y}, z};
            CCIntersection(a[i], mid, sect);
        }
        double ans = 0, tmp;
        for (int i = 0; i < sect.size(); i++)
            for (int j = i+1; j < sect.size(); j++) {
                if ((tmp = Length(sect[i]-sect[j])) > ans) ans = tmp;
            }
        printf("Case #%d: %.15f\n", ca, check() ? 2*r : ans);
    }
}

Guess you like

Origin www.cnblogs.com/ruthank/p/11366209.html