Topic Portal
Test instructions: A pipe, a light source emitted from the entrance, ask the source of the farthest reaches the place.
Analysis: Examples in black Book, the solution is to enumerate an arbitrary upper vertex and a lower vertex (optimized), the formation of a straight line, if the line and all vertical line segments have intersections, it means that can pass through the pipeline.
/************************************************* author:running_time* Created time:2015/10/31 Saturday 10:28:12* Fi Le Name:P oj_1039.cpp ************************************************/#include <cstdio> #include < algorithm> #include <iostream> #include <sstream> #include <cstring> #include <cmath># Include <string> #include <vector> #include <queue> #include <deque> #include <stack># Include <list> #include <map> #include <set> #include <bitset> #include <cstdlib> #include <ctime>using namespace std; #define Lson L, Mid, RT << 1#define Rson mid + 1, R, RT << 1 | 1typedef long ll;const int N = 1e5 + 10;const int INF = 0x3f3f3f3f;const int MOD = 1e9 + 7;const Double EPS = 1e-10;c Onst Double PI = ACOs ( -1.0), int dcmp (double x) {//three state function, reduced accuracy problem if (fabs (x) < EPS) return 0; else return x < 0? -1:1;} struct Point {//points defined by double x, y; Point() {} point (double x, double y): X (x), Y (y) {}-operator + (const point &r) const {//vector addition return point (x + r.x, y + r.y); } Point operator-(const point &r) const {//Vector subtraction return point (x-r.x, Y-R.Y); } Point operator * (double p) const {//vector multiplied by a scalar return point (x * p, Y * p); } point operator/(double p) const {//vector divided by scalar return point (x/p, y/p); } BOOL operator < (const point &r) const {//DOT coordinate sort return x < R.x | | (x = = r.x && y < r.y); } bool operator = = (Const point &r) const {//judgment same dot return dcmp (x-r.x) = = 0 && dcmp (y-r . y) = = 0; }};typedef Point Vector; Vector definition point read_point (void) {//points read in double x, y; scanf ("%lf%lf", &x, &y); Return point (x, y);} Double dot (vector A, vector B) {//vector dot product return a.x * b.x + a.y * B.Y;} Double Cross (vector A, vector B) { Vector Fork Product Return a.x * B.Y-A.Y * b.x;} Double Polar_angle (vector A) {//Vector polar return atan2 (A.Y, a.x);} Double length (vector a) {//vector length, dot product return sqrt (dot (A, a));} Double angle (vector a, vector b) {//Vector corner, counterclockwise, dot product return ACOs (dot (A, b)/Length (a)/length (b));} Vector Rotate (vector A, double rad) {//vector rotation, counter-clockwise return vector (a.x * cos (RAD)-A.y * sin (rad), a.x * sin (rad ) + a.y * cos (RAD));} Vector Nomal (vector a) {//vector double len = length (a) of the unit method vectors; Return Vector (-a.y/len, A.x/len);} Point Line_line_inter (point P, Vector V, point q, Vector W) {//two line intersection, parametric equation Vector U = p-q; Double T = Cross (w, U)/Cross (V, W); return p + V * t;} Double Point_to_line the distance from {//points to a straight line, two-point Vector V1 = b-a, V2 = p-a; Return Fabs (Cross (V1, V2))/Length (V1);} Double point_to_seg the distance from {//points to a line segment, two-point if (a = = b) return length (P-A); Vector V1= b-a, V2 = p-a, V3 = P-b; if (DCMP (dot (V1, V2)) < 0) return length (V2); else if (dcmp (dot (V1, V3)) > 0) return length (V3); else return Fabs (cross (V1, V2))/Length (V1);} Point Point_line_proj (point P, points a, dot b) {//dots are projected on a line, two points Vector V = b-a; Return a + v * (dot (v, p-a)/dot (V, v));} BOOL Can_seg_seg_inter (Points A1, point A2, Spot b1, dot b2) {//Judgment segment intersection, two-bit double C1 = Cross (A2-A1, b1-a 1), C2 = Cross (A2-A1, b2-a1), C3 = Cross (B2-B1, a1-b1), C4 = Cross (b2-b1, A2-B1); Return DCMP (C1) * DCMP (C2) < 0 && dcmp (C3) * DCMP (C4) < 0;} BOOL Can_line_seg_inter (Point A1, Point A2, Point-B1, point-B2) {Double C1 = Cross (A2-A1, b1-a1), C2 = Cross ( A2-A1, B2-A1); Return DCMP (C1 * C2) <= 0;} BOOL On_seg (point P, bit A1, points A2) {//Judgment dot on segment, two-point return dcmp (Cross (a1-p, a2-p)) = = 0 && DCMP (dot (a1-p, a2-p)) < 0;} Double ARea_triangle (Point A, point B, point C) {//triangular area, fork product return Fabs (Cross (b-a, c-a))/2.0;} Double Area_poly (point *p, int n) {//Polygon area, cross product double ret = 0; for (int i=1; i<n-1; ++i) {ret + = Fabs (Cross (P[i]-p[0], p[i+1]-p[0])); } return RET/2;} /* Point set convex hull, a collection of input points, returns a collection of convex hull points. If you do not wish to have an input point on the side of the convex hull, change the two <= to <*/vector<Point> Convex_hull (vector<point> PS) {sort (Ps.begin (), Ps.end ());//x-y sort ps.erase (Unique (Ps.begin (), Ps.end ()), Ps.end ());//delete duplicate point int n = ps.size (), k = 0; Vector<point> QS (n * 2); for (int i=0; i<n; ++i) {when (K > 1 && Cross (qs[k-1]-qs[k-2], Ps[i]-qs[k-1]) <= 0) k--; qs[k++] = ps[i]; } for (int i=n-2, t=k; i>=0;-I.) {while (K > t && Cross (Qs[k-1]-qs[k-2], Ps[i]-qs[k-1]) &L t;= 0) k--; qs[k++] = ps[i]; } qs.resize (k-1); return QS;} 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); }};struct Line {point P; Vector v; Double R; Line () {} line (const point &p, const Vector &v): P (P), V (v) {r = Polar_angle (v); } Point point (Double A) {return P + v * A; }};/* Line intersection to find the intersection, return the number of intersections, the intersection is saved in P */int line_cir_inter (lines L, Circle C, double &t1, double &t2, vector<point> &P) {Double A = l.v.x, B = l.p.x-c.c.x, C = l.v.y, d = l.p.y-c.c.y; Double E = A * a + c * C, F = 2 * (A * b + c * d), G = b * B + d * D-C.R * C.R; Double delta = f * f-4 * e * g; if (dcmp (delta) < 0) return 0; if (dcmp (delta) = = 0) {T1 = t2 =-F/(2 * e); P.push_back (L.point (t1)); return-1; } T1 = (-f-sqrt (delta))/(2 * e); P.push_back (L.point (t1)); T2 = (-f + sqrt (delta))/(2 * e); P.push_back (L.point (T2)); if (dcmp (T1) < 0 | | DCMP (T2) < 0) return 0; return 2;} /* Two circle intersection to find the intersection, return the number of intersections. The intersection is saved in P */int Cir_cir_inter (Circle C1, Circle C2, vector<point> &p) {Double d = length (c1.c-c2.c); if (dcmp (d) = = 0) {if (dcmp (C1.R-C2.R) = = 0) return-1; Two circles overlap else 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 = Polar_angle (c2.c-c1.c); Double da = ACOs ((C1.R * C1.R + d * D-C2.R * C2.R)/(2 * C1.R * d)); C1C2 to C1p1 's horn? Point P1 = C1.point (a-da), p2 = c2.point (A + da); P.push_back (p1); if (P1 = = p2) return 1; else P.push_back (p2); return 2;} /* Go to the tangent of the circle, return the number of tangent lines, keep the tangent in V */int Point_cir_tan (point P, Circle C, vector *v) {vector u = c.c-p; Double dis = length (u); if (Dis < C.R) return 0; else if (dcmp (DIS-C.R) = = 0) {V[0] = rotate (u, PI/2); return 1; } else {Double ang = asin (C.R/DIS); v[0] = rotate (u,-ang); V[1] = rotate (u, +ang); return 0; }}/* two round Gongsche, return Gongsche number, tangent short point saved in A and B */int Cir_cir_tan (Circle A, Circle B, point *a, point *b) {int cnt = 0; if (A.R < B.R) {swap (A, B); Swap (A, b); } Double D = dot (a.c-b.c, A.C-B.C); Double rsub = A.R-B.R, rsum = A.R + B.R; if (dcmp (D-rsub) < 0) return 0; Contains double base = Polar_angle (B.C-A.C); if (dcmp (d) = = 0 && dcmp (A.R-B.R) = = 0) return-1; Two round overlapping if (dcmp (d-rsub) = = 0) {//inscribed, one tangent a[cnt] = A.point (base); B[CNT] = B.point (base); cnt++; return 1; }//has Wei Panche double ang = ACOs (rsub/d); A[CNT] = A.point (base + ang); B[CNT] = B.point (base + ang); cnt++; A[CNT] = A.point (Base-ang); B[CNT] = B.point (Base-ang); cnt++; if (d = = Rsum) {a[cnt] = A.point (base); B[CNT] = B.point (base + PI); cnt++; } else if (dcmp (d-rsum) > 0) {//two strips Netache DOuble ang2 = ACOs (rsum/d); A[CNT] = A.point (base + ang2); B[CNT] = B.point (base + ang2 + PI); cnt++; A[CNT] = A.point (base-ang2); B[CNT] = b.point (base-ang2 + PI); cnt++; } return CNT;} Point p1[22], p2[22], p3;int main (void) {int n; while (scanf ("%d", &n) = = 1) {if (!n) break; for (int i=1; i<=n; ++i) {P1[i] = Read_point (); P2[i] = Point (p1[i].x, p1[i].y-1); } bool flag = FALSE; Double ans = p1[1].x; for (int i=1, i<=n &&!flag; ++i) {for (int j=1; j<=n &&!flag; ++j) { if (i = = j) Continue; int k; for (k=1; k<=n; ++k) {if (!can_line_seg_inter (P1[i], p2[j], p1[k], p2[k])) { Break }} if (k = = n + 1) {flag = true; Break } else if (k > Max (i, J)) {p3 = Line_line_inter (P1[i], p2[j]-p1[i], p1[k-1], P1[k]-p1[k-1]); ans = max (ans, p3.x); P3 = Line_line_inter (P1[i], p2[j]-p1[i], p2[k-1], P2[k]-p2[k-1]); ans = max (ans, p3.x); }}} if (!flag) {printf ("%.2f\n", ans); } else puts ("Through all the pipe."); }//cout << "time Elapsed:" << 1.0 * Clock ()/clocks_per_sec << "s.\n"; return 0;}
Simple geometry (lines intersect line segments) POJ 1039 Pipe