Preliminary computational geometry (brush Blue Book)

 

head File

#include<bits/stdc++.h>
#define max(a,b) (a>b?a:b)
#define min(a,b) (a<b?a:b)
using namespace std;
typedef long long ll;
const int maxn = 1e3+7;
const double esp = 1e-6;
int dcmp(double x){
    if(fabs(x)<esp)return 0;
    return x<0?-1:1;
}
struct Point{
    double x,y;
    void read(){scanf("%lf%lf",&x,&y);}
    Point(double x = 0,double y = 0):x(x),y(y){}
};
double Cross(const Point A,const Point B){ return A.x*B.y-A.y*B.x; }
double Dot(const Point A,const Point B){ return A.x*B.x+A.y*B.y; }
double Len(const Point A){ return sqrt(Dot(A,A)); }
double Angle(const Point A,const Point B){ return acos(Dot(A,B)/Len(A)/Len(B)); }
Point operator + (const Point A,const Point B){ return Point(A.x+B.x,A.y+B.y); }
Point operator - (const Point A,const Point B){ return Point(A.x-B.x,A.y-B.y); }
Point operator * (const Point A,const double B){ return Point(A.x*B,A.y*B); }
Point operator / (const Point A,const double B){ return Point(A.x/B,A.y/B); }
Point Rotate(const Point A,double rad){return Point(A.x*cos(rad)-A.y*sin(rad),A.x*sin(rad)+A.y*cos(rad));}
//负数表示顺时针
Point Normal(const Point A){return Point(-A.y/Len(A),A.x/Len(A));}//法向量
bool operator == (const Point A,const Point B){return !dcmp(A.x-B.x)&&!dcmp(A.y-B.y); }
bool operator != (const Point A,const Point B){return !(A == B);}
bool operator < (const Point A,const Point B){return A.x<B.x || (A.x == B.x&&A.y<B.y);}
typedef Point Vector;
struct Circle{
    Point x;
    double r;
    void read(){
        x.read();
        scanf("%lf",&r);
    }
};
bool quickRepel(Point x1,Point y1,Point x2,Point y2){//快速排斥
    Point Lx = Point(min(x1.x,y1.x),min(x1.y,y1.y));
    Point Rx = Point(max(x1.x,y1.x),max(x1.y,y1.y));

    Point Ly = Point(min(x2.x,y2.x),min(x2.y,y2.y));
    Point Ry = Point(max(x2.x,y2.x),max(x2.y,y2.y));

    Point L = Point(max(Lx.x,Ly.x),max(Lx.y,Ly.y));
    Point R = Point(min(Rx.x,Ry.x),min(Rx.y,Ry.y));

    return (L.x<=R.x) && (L.y<=R.y);
}
bool OnSegment(Point P,Point x,Point y){//点在线段上
    if(P == x||P == y)return 1;
    return! dCMP (Cross (xP, yP)) && dCMP (Dot (Px, Py)) < 0 ; 
} 
BOOL straddle which in (Point X1, Point Y1, Point X2, Point Y2) { // straddle experiments (line segment intersection point) 
    IF (! quickRepel (X1, Y1, X2, Y2)) return  0 ;
     Double C1 = Cross (Y1-X1, X2-X1), C2 = Cross (X1-Y1, Y2 - X1);
     Double C3 = Cross (Y2 -x2, X1-X2), C4 = Cross (Y2-X2, Y1- X2);
     return dCMP (C1) * dCMP (C2) <= 0 && dCMP (C3) * dCMP (C4) <= 0 ;
     // allow partial overlap or coincide with the endpoint
     // return dCMP (C1) * dCMP (C2) <0 && dCMP (C3) * dCMP (C4) <0;
     // must not only a point of intersection on the endpoint
 }
LinearIntersection Point (Point P, the Vector V, Point Q, the Vector W) { // Solutions line intersection 
    Assert (V = W!); // Parallel lines parallel to 
    the Vector U = the P- Q;
     Double T = Cross (W, U) / Cross (V, W);
     return P + V * T; 
} 
point GetLineProjection (point P, point a, point B) { // P projected to a point on AB 
    the Vector V = the B- a;
     return a + V * (dot (V, PA) / dot (V, V)); 
} 
point SymmetricPoint (point P, point a, point B) { // P about symmetry points AB 
    return GetLineProjection (P, a, B) * 2.0 - P; 
} 
DoubleDistanceToline (Point P, Point A, Point B) { // points to a straight line from 
    the Vector BA = V1, V2 = the P- A;
     return FABS (Cross (V1, V2)) / Len (V1); 
} 
Double DistanceToSegment (Point P, point A, point B) { // point of the line segment to the 
    IF (A == B) return Len (PA ); 
    the Vector V1 = BA, PA = V2, V3 = the P- B;
     IF (dCMP (dot (V1, V2)) < 0 ) return Len (V2);
     IF (dCMP (Dot (V1, V3))> 0 ) return Len (V3);
     return FABS (Cross (V1, V2)) / Len (V1) ; 
}
View Code

 

example:

Morley's Theorem

https://vjudge.net/problem/UVA-11178

Note appreciated angle trisection concept and not a side trisection

Point GetPoint(Point A,Point B,Point C){
    Vector v1 = C-B;
    double a1 = Angle(A-B,v1);
    v1 = Rotate(v1,a1/3);

    Vector v2 = B-C;
    double a2 = Angle(A-C,v2);
    v2 = Rotate(v2,-a2/3);
    return LinearIntersection(B,v1,C,v2);
}
int main(){
    int T;
    scanf("%d",&T);
    while(T--){
        Point A,B,C;
        A.read(),B.read(),C.read();
        Point D = GetPoint(A,B,C);
        Point E = GetPoint(B,C,A);
        Point F = GetPoint(C,A,B);
        printf("%.6f %.6f ",D.x,D.y);
        printf("%.6f %.6f ",E.x,E.y);
        printf("%.6f %.6f\n",F.x,F.y);
    }
    return 0;
}

 

A nice stroke LA3263

= = I did not find this title

 

From dog

https://vjudge.net/problem/UVA-11796

Because there is no acceleration, so can a dog as a frame of reference, consider another dog contribution

Each transition at least one point, so the complexity can be secured up to n + m

Analog to

Point A[maxn],B[maxn];
double Max,Min;
void update(Point P,Point A,Point B){
    Min = min(Min,DistanceToSegment(P,A,B));
    Max = max(Max,Len(P-A));
    Max = max(Max,Len(P-B));
}
int main(){
    int T,n,m,Case = 0;
    scanf("%d",&T);
    while(T--){
        scanf("%d%d",&n,&m);
        for(int i=0;i<n;i++)A[i].read();
        for(int i=0;i<m;i++)B[i].read();
        double LenA = 0,LenB = 0;
        for(int i=0;i<n-1;i++) LenA += Len(A[i+1]-A[i]);
        for(int i=0;i<m-1;i++) LenB += Len(B[i+1]-B[i]);
        int Sa = 0,Sb = 0;
        Point Pa = A[0],Pb = B[0];
        Min = 1e9,Max = -1e9;
        while(Sa<n-1 && Sb<m-1){
            double La = Len(A[Sa+1]-Pa);
            double Lb = Len(B[Sb+1]-Pb);
            double T = min(La/LenA,Lb/LenB);
            Vector Va = (A[Sa+1]-Pa)/La*T*LenA;
            Vector Vb = (B[Sb+1]-Pb)/Lb*T*LenB;
            update(Pa,Pb,Pb+Vb-Va);
            Pa = Pa+Va;
            Pb = Pb+Vb;
            if(Pa == A[Sa+1])Sa++;
            if(Pb == B[Sb+1])Sb++;
        }
        printf("Case %d: %.0f\n",++Case,Max-Min);
    }
    return 0;
}

 

Guess you like

Origin www.cnblogs.com/revolIA-room/p/11620622.html