UVA 12307-smallest enclosing Rectangle (rotating jam)

Source: Internet
Author: User
Tags acos

Topic Link: UVA 12307-smallest enclosing Rectangle


The two pairs of heel-to-point circumference are rectangular, and the minimum values of all feasible rectangles are enumerated.


#include <cstdio> #include <cstring> #include <cmath> #include <vector> #include <complex > #include <algorithm>using namespace std;typedef pair<int,int> pii;const Double pi = 4 * atan (1); Const Doub Le EPS = 1e-10;inline int dcmp (double x) {if (Fabs (x) < EPS) return 0; else return x < 0? -1:1;} Inline double getdistance (double x, double y) {return sqrt (x * x + y * y);} Inline double Torad (double deg) {return deg/180 * PI;} struct point {double x, y; Point (Double x = 0, double y = 0): x (x), Y (y) {}void read () {scanf ("%lf%lf", &x, &y);} void Write () {printf ("%lf%lf", x, y);} BOOL operator = = (CONST point& u) Const {return dcmp (x-u.x) = = 0 && dcmp (y-u.y) = = 0;} BOOL operator! = (const point& u) Const {return! ( *this = = u); }bool operator < (const point& u) Const {return x < u.x | | (x = = u.x && y < u.y); }bool operator > (const point& u) Const {return u < *this;} BOOL OperAtor <= (const point& u) Const {return *this < u | | *this = u;} BOOL operator >= (const point& u) const {return *this > U | | *this = u;} Point operator + (const point& u) {return point (x + u.x, y + u.y);} Point operator-(const point& u) {return point (x-u.x, y-u.y);} Point operator * (const double u) {return point (x * u, y * u);} Point operator/(const double u) {return point (x/u, y/u);} Double operator * (const point& u) {return x*u.y-y*u.x;}}; typedef point VECTOR;TYPEDEF vector<point> polygon;struct line {Double A, B, C; Line (Double A = 0, double b = 0, double c = 0): A (a), B (b), C (c) {}};struct dirline {point P; Vector v;double Ang;dirline () {}dirline (point P, Vector v): P (P), V (v) {ang = atan2 (V.y, v.x);} BOOL operator < (const dirline& u) const {return Ang < U.ang;}}; struct Circle {point o;double R; Circle () {}circle (Point O, double r = 0): O (O), R (r) {}void read () {o.read (), scanf ("%lf", &r);} PointPoint (Double rad) {return point (o.x + cos (rad) *r, O.y + sin (rad) *r);} Double Getarea (double rad) {return rad * R * R/2;}}; Namespace punctual {Double getdistance (point A, point B) {double x=a.x-b.x, y=a.y-b.y; return sqrt (x*x + y*y);}};  namespace Vectorial {/* dot product: The product of two vector lengths multiplied by the cosine of their angle, the angle is greater than 90 degrees the product is negative */double Getdot (vector A, vector b) {return a.x * b.x + A.Y * B.Y;  }/* Cross product: The cross product is equal to two vectors consisting of a triangle with a direction area of twice times, crosses (V, w) =-cross (W, v) */double Getcross (vector A, vector b) {return a.x * B.Y-A.Y * b.x; }double GetLength (Vector a) {return sqrt (Getdot (A, a));} Double Getplength (Vector a) {return Getdot (A, a);} Double Getangle (Vector u) {return atan2 (u.y, u.x);} Double Getangle (vector A, vector b) {return ACOs (Getdot (A, B)/GetLength (a)/GetLength (b));} Vector Rotate (vector A, double rad) {return vector (A.x*cos (RAD)-a.y*sin (RAD), A.x*sin (RAD) +a.y*cos (RAD));} /* unit normal */vector Getnormal (Vector a) {double L = getlength (a); return Vector (-a.y/l, a.x/l);}}; Namespace Complexvector {TypEdef complex<double> point;typedef point vector;double getdot (vector A, vector b) {return real (Conj (a) *b);} Double Getcross (vector A, vector b) {return imag (Conj (a) *b); Vector Rotate (vector A, double rad) {return a*exp (point (0, RAD));}}; Namespace Linear {using namespace vectorial; Line GetLine (double x1, double y1, double x2, double y2) {return line (y2-y1, x1-x2, y1*x2-x1*y2);} Line GetLine (double A, double b, point u) {return line (A, B, u.y * b-u.x * a);} BOOL Getintersection (line p, line Q, point& o) {if (Fabs (P.A * q.b-q.a * p.b) < EPS) return false;o.x = (Q.C * p. B-P.C * q.b)/(P.A * q.b-q.a * p.b); o.y = (Q.C * p.a-p.c * q.a)/(P.B * q.a-q.b * p.a); return true;} /* Intersection of linear PV and line QW */bool getintersection (point P, Vector v, point Q, Vector W, point& o) {if (dcmp (Getcross (V, w)) = = 0 ) return false; Vector u = p-q;double k = Getcross (w, u)/Getcross (V, w); o = p + v * K;return true;} /* point P to line ab distance */double getdistancetolineb) {return fabs (Getcross (b-a, p-a)/GetLength (B-A));} Double getdistancetosegment (point P, point A, point B) {if (a = = b) return getlength (P-A); Vector v1 = b-a, v2 = p-a, V3 = p-b;if (dcmp (Getdot, V1) < 0) return v2 (getlength); else if (V2 (dcmp (Getdot, V 3)) > 0) return GetLength (V3), Else return fabs (Getcross (v1, v2)/GetLength (v1));} /* point P on the line ab projection */point getpointtoline (points P, a, point B) {Vector v = b-a; return a+v* (Getdot (V, p-a)/Getdot (V, v)); }/* to determine if a segment has an intersection */bool haveintersection (Point A1, Point A2, point B1, point B2) {double C1=getcross (a2-a1, b1-a1), c2=getc Ross (A2-A1, B2-A1), C3=getcross (B2-B1, A1-B1), C4=getcross (B2-B1,A2-B1), return dcmp (C1) *dcmp (C2) < 0 && dcmp (C3) *dcmp (C4) < 0;} /* Determine if the point is */bool onsegment on a line segment {return dcmp (Getcross (A-p, b-p)) = = 0 && dcmp (Getdot (A- P, b-p)) < 0; }bool Onleft (dirline L, point P) {return dcmp (L.V * (P-L.P)) > 0;}} Namespace triangular {using namespace VectoriAl;double Getangle (Double A, double b, double c) {return ACOs ((a*a+b*b-c*c)/(2*a*b));} Double Getarea (double A, double b, double c) {double s = (a+b+c)/2; return sqrt (s* (s-a) * (s-b) * (S-C));} Double Getarea (Double A, double h) {return a * H/2;} Double Getarea (Point A, point B, point C) {return fabs (Getcross (b-a, c-a))/2;} Double Getdirarea (Point A, point B, point C) {return Getcross (b-a, c-a)/2;}};  Namespace polygonal {using namespace vectorial;using namespace linear;double getarea (point* p, int n) {double ret = 0;for (int i = 0; i < n-1; i++) ret + = (p[i]-p[0]) * (p[i+1]-p[0]); return RET/2;} /* Convex package */int getconvexhull (point* p, int n, point* ch) {sort (p, p + N); int m = 0;for (int i = 0; i < n; i++) {/* collinear */ while (M > 1 && dcmp (Getcross (ch[m-1]-ch[m-2), p[i]-ch[m-1]) < 0) M--;while (M > 1 && dcmp (get Cross (Ch[m-1]-ch[m-2], p[i]-ch[m-1])) <= 0) m--;ch[m++] = P[i];} int k = m;for (int i = n-2; I >= 0; i--) {/* collinear *///while (M > K && dcmp (Getcross (Ch[m-1]-ch[m-2], p[i]-ch[m-2]) < 0) M--;while (M > K && dcmp (Getcross (ch[m -1]-ch[m-2], p[i]-ch[m-2])) <= 0) m--;ch[m++] = P[i];} if (n > 1) m--;return m;} int Ispointinpolygon (Point O, point* p, int n) {int wn = 0;for (int i = 0; i < n; i++) {int J = (i + 1)% n;if (onsegm ENT (o, p[i], p[j])) return 0; the boundary int k = dcmp (Getcross (P[j]-p[i], o-p[i])); int D1 = DCMP (p[i].y-o.y); int d2 = DCMP (P[J].Y-O.Y); if (k > 0 &am p;& D1 <= 0 && d2 > 0) wn++;if (k < 0 && D2 <= 0 && d1 > 0) wn--;} Return WN? -1:1;} /* Rotate Jam */void rotatingcalipers (point *p, int n, vector<pii>& sol) {sol.clear (); int j = 1; P[n] = p[0];for (int i = 0; I < n; i++) {while (Getcross (p[j+1]-p[i+1], p[i]-p[i+1]) > Getcross (p[j]-p[i+1], p[i]-p[i+1])) j = (j+1)% N;sol.push_back ( Make_pair (i, J)); Sol.push_back (Make_pair (i + 1, j + 1));}} void Rotatingcalipersgetrectangle (Point *p, Int. N, double& area, DOUBLe& perimeter) {P[n] = p[0];int L = 1, R = 1, j = 1;area = perimeter = 1e20;for (int i = 0; i < n; i++) {Vector v = (P[i+1]-p[i])/GetLength (P[i+1]-p[i]), while (DCMP (Getdot (V, p[r%n]-p[i))-Getdot (V, p[(r+1)%n]-p[i])) < 0) r++; while (J < R | | dcmp (Getcross (V, p[j%n]-p[i])-Getcross (v,p[(j+1)%n]-p[i])) < 0) J++;while (L < J | | dcmp (GETDOT  (V, P[l%n]-p[i])-Getdot (V, p[(l+1)%n]-p[i])) > 0) l++;d ouble w = Getdot (V, P[r%n]-p[i])-getdot (V, p[l%n]-p[i]);d ouble h = getdistancetoline (p[j%n], p[i], p[i+1]), area = min (area, W * h);p erimeter = min (Perimeter, 2 * w + 2 * h);}} /* Calculate the half plane intersection can be used increment method, O (n^2), initially set 4 infinity half plane *//* with a straight line a->b cut polygon U, return to the left.  May degenerate into a single point or segment */polygon Cutpolygon (Polygon u, point A, point B) {Polygon Ret;int n = u.size (); for (int i = 0; i < n; i++) {Point c = u[i], d = u[(i+1)%n];if (dcmp ((b-a) * (c-a)) >= 0) Ret.push_back (c); if (dcmp ((b-a) * (c-d))! = 0) {Point T;geti Ntersection (A, b-a, C, d-c, T); if (Onsegment (t, C, D)) Ret.push_back (t);}} return ret;} /* Half plane intersect */int halfplaneintersection (dirline* li, int n, point* poly) {sort (Li, Li + N); int first, last; point* p = new Point[n];D irline* q = new Dirline[n];q[first=last=0] = li[0];for (int i = 1; i < n; i++) {while (First & Lt Last &&!onleft (Li[i], p[last-1]) Last--;while (First < last &&!onleft (Li[i], P[first])) first++;q[+ +last] = li[i];if (dcmp (Q[LAST].V * q[last-1].v) = = 0) {last--;if (Onleft], q[last)) LI[I].P] = Q[last];} if (first < last) getintersection (Q[LAST-1].P, Q[LAST-1].V, Q[LAST].P, Q[LAST].V, p[last-1]);} while (first < last &&!onleft (Q[first], p[last-1)) last--;if (Last-first <= 1) {delete [] p; Delete [] Q return 0; }getintersection (Q[LAST].P, Q[LAST].V, Q[FIRST].P, Q[FIRST].V, p[last]); int m = 0;for (int i = first; I <= last; i++) p oly[m++] = p[i];d elete [] p; Delete [] Q;return m;}; Namespace Circular {using namespace Linear;using namespace vectorial;using namespace triangular;/* straight and original intersection */int Getlinec Ircleintersection (POint p, point Q, Circle O, double& t1, double& T2, vector<point>& sol) {vector v = q-p;/* need to empty sol before use */ Sol.clear ();d ouble a = v.x, B = p.x-o.o.x, c = v.y, d = p.y-o.o.y;double e = a*a+c*c, F = (a*b+c*d), G = B*b+d*d-o . r*o.r;double Delta = f*f-4*e*g;if (dcmp (Delta) < 0) return 0;if (dcmp (delta) = = 0) {T1 = t2 =-F/(2 * e); sol.push_ Back (p + v * t1); return 1;} T1 = (-f-sqrt (delta))/(2 * e); Sol.push_back (p + v * t1); t2 = (-f + sqrt (delta))/(2 * e); Sol.push_back (p + v * T2); return 2;} /* Circle intersection */int getcirclecircleintersection (Circle O1, Circle O2, vector<point>& sol) {Double d = getlength (O1. O-O2.O); if (dcmp (d) = = 0) {if (dcmp (O1.R-O2.R) = = 0) Return-1;return 0;} if (dcmp (O1.R + o2.r-d) < 0) return 0;if (DCMP (fabs)-D) > 0) return O1.R-O2.R a = 0;double (Getangle) ;d ouble da = ACOs ((O1.R*O1.R + D*D-O2.R*O2.R)/(2*o1.r*d)); Point P1 = O1.point (a-da), p2 = O1.point (A+da), Sol.push_back (p1), if (P1 = = p2) return 1;sol.Push_back (p2); return 2;} /* tangents */int gettangents (point P, Circle O, vector* v) {Vector U = o.o-p;double d = getlength (u); if (d < O.R) R Eturn 0;else if (dcmp (D-O.R) = = 0) {V[0] = rotate (u, PI/2); return 1;} else {double ang = asin (O.R/D); v[0] = rotate (u ,-ang); v[1] = rotate (U, ANG); return 2;}} /* A[i] and b[i] are the tangency points of the section I tangent on O1 and O2 respectively */int gettangents (Circle O1, Circle O2, point* A, point* b) {int cnt = 0;IF (O1.R < O2.R) {swap (O1, O2); swap (A, b);} Double D2 = GetLength (O1.O-O2.O); D2 = D2 * d2;double rdif = O1.R-O2.R, rsum = O1.R + o2.r;if (D2 < RDIF * Rdif) return 0;if (dcmp (d2) = = 0 && DCMP (O1.R-O2.R) = = 0) return-1;double base = Getangle (O2.O-O1.O); if (dcmp (D2-RDIF * rdif) = = 0) {a[cnt] = O1.point ( Base); B[CNT] = O2.point (base); Cnt++;return CNT;} Double ang = ACOs ((O1.R-O2.R)/sqrt (D2)); a[cnt] = O1.point (Base+ang); B[CNT] = O2.point (Base+ang); CNT++;A[CNT] = O1.point (Base-ang); B[CNT] = O2.point (Base-ang); Cnt++;if (dcmp (d2-rsum * rsum) = =0) {a[cnt] = O1.point (base); b[cnt] = O2.point (base); cnt++;} else if (D2 > Rsum * rsum) {double ang = ACOs ((O1.R + O2 . R)/sqrt (D2)); a[cnt] = O1.point (Base+ang); B[CNT] = O2.point (Base+ang); CNT++;A[CNT] = O1.point (Base-ang); B[CNT] = O2.point (Base-ang); cnt++;} return CNT;}  /* Three points to determine the tangent circle */circle circumscribedcircle (Point P1, Spot, point P3) {Double Bx = p2.x-p1.x, by = P2.Y-P1.Y;  Double Cx = p3.x-p1.x, Cy = p3.y-p1.y;  Double D = 2 * (Bx * cy-by * Cx);  Double CX = (Cy * (BX * bx + by *) – by * (CX * CX + cy * cy))/D + p1.x;  Double cy = (BX * (CX * CX + cy * CY)-CX * (BX * bx + by *))/D + p1.y;  Point P = Point (CX, CY);  Return Circle (P, GetLength (p1-p));  }/* three to determine inscribed circle */circle inscribedcircle (Point P1, points P2, dot p3) {Double A = GetLength (P2-P3);  Double b = getlength (P3-P1);  Double c = getlength (P1-P2);  Point P = (P1 * A + P2 * b + p3 * c)/(A + B + c);  Return Circle (P, Getdistancetoline (P, p1, p2)); }/* Triangle One vertex is the center */double getpubliCareatotriangle (Circle O, point A, point B) {if (dcmp ((A-O.O) * (b-o.o)) = = 0) return 0;int sig = 1;double da = getplength ( O.O-A), db = Getplength (O.o-b), if (dcmp (DA-DB) > 0) {swap (DA, db), swap (A, b); sig =-1;} Double T1, t2;vector<point> sol;int n = getlinecircleintersection (A, B, O, T1, T2, Sol); if (dcmp (DA-O.R*O.R) <= 0 {if (dcmp (DB-O.R*O.R) <= 0) return Getdirarea (O.O, A, b) * Sig;int k = 0;if (Getplength (sol[0]-b) > Getplength (sol[ 1]-b)) K = 1;double ret = Getarea (o.o, A, sol[k]) + O.getarea (Getangle (SOL[K]-O.O, b-o.o));d ouble tmp = (a-o.o) * (B-O.O); re TURN ret * SIG * DCMP (TMP);}  Double d = getdistancetosegment (o.o, A, B), if (dcmp (D-O.R) >= 0) {DOUBLE ret = O.getarea (Getangle (A-O.O, b-o.o));d ouble TMP = (A-O.O) * (B-O.O); return ret * sig * DCMP (TMP);} Double K1 = o.r/getlength (a-o.o), K2 = O.r/getlength (B-O.O); Point P = o.o + (a-o.o) * K1, q = o.o + (b-o.o) * k2;double Ret1 = O.getarea (Getangle (P-O.O, q-o.o));d ouble Ret2 = o.g Etarea (Getangle (SOL[0]-O.O, SOL[1]-O.O)-Getarea (O.O, sol[0], sol[1]);d ouble ret = (ret1-ret2), TMP = (A-O.O) * (B-O.O); return ret * sig * DCMP (TMP);  }double Getpublicareatopolygon (Circle O, point* p, int n) {if (dcmp (O.R) = = 0) return 0;double area = 0;for (int i = 0; i < n; i++) {int u = (i + 1)% n;area + = Getpublicareatotriangle (O, P[i], p[u]);} return Fabs (area);}}; Using namespace Polygonal;//void rotatingcalipersgetrectangle (point *p, int n, double& area, double& perimeter) { const int MAXN = 1e5 + 5;int N; Point P[MAXN], Ch[maxn];int main () {while (scanf ("%d", &n) = = 1 && N) {for (int i = 0; i < N; i++) p[i].re AD (); N = Getconvexhull (P, N, ch);d ouble area, Perimeter;rotatingcalipersgetrectangle (CH, n, area, perimeter);p rintf ("%.2lf%. 2lf\n ", area, perimeter);} return 0;}


Copyright NOTICE: This article for Bo Master original article, without Bo Master permission not reproduced.

UVA 12307-smallest enclosing Rectangle (rotating jam)

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.