int sgn(double x){return x<-eps?-1:x<eps?0:1;} struct Point{ double x,y; Point(){} Point(double _x,double _y){ x=_x;y=_y; } }; struct Seg{ Point s,e; Seg(){} Seg(Point _s,Point _e){ s=_s;e=_e; } Seg(double a,double b,double c,double d){ s.x=a;s.y=b; e.x=c;e.y=d; } }; double cross(Point a,Point b,Point c){ return (b.x-a.x)*(c.y-a.y)-(b.y-a.y)*(c.x-a.x); } double dist(Point a,Point b){ return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y)); } /*两线段交点*/ Point inter(Seg a,Seg b){ Point p1,p2,p3,p4; p1=a.s;p2=a.e;p3=b.s;p4=b.e; double a1=p1.y-p2.y; double b1=p2.x-p1.x; double c1=p1.x*p2.y-p2.x*p1.y; double a2=p3.y-p4.y; double b2=p4.x-p3.x; double c2=p3.x*p4.y-p4.x*p3.y; double x=(c2*b1-c1*b2)/(a1*b2-a2*b1); double y=(c2*a1-c1*a2)/(a2*b1-a1*b2); return Point(x,y); } /*线段相交*/ bool jiao(Seg a,Seg b){ Point p1,p2,p3,p4; p1=a.s;p2=a.e; p3=b.s;p4=b.e; if(min(p1.x,p2.x)<=max(p3.x,p4.x) && min(p3.x,p4.x)<=max(p1.x,p2.x) && min(p1.y,p2.y)<=max(p3.y,p4.y) && min(p3.y,p4.y)<=max(p1.y,p2.y) && sgn(cross(p1,p2,p3))*sgn(cross(p1,p2,p4))<=0 && sgn(cross(p3,p4,p1))*sgn(cross(p3,p4,p2))<=0 ) return true; return false; } /*凸包graham算法*/ Point tmp; bool cmp(const Point &a,const Point &b){ int ret=sgn(cross(tmp,a,b)); if(ret==0) return dist(tmp,a)<dist(tmp,b); return ret>0; } int graham(Point p[],int n,Point convex[]){ int mi=0; for(int i=1;i<n;i++) if(sgn(p[mi].y-p[i].y)>0 || sgn(p[mi].y-p[i].y)==0 && sgn(p[mi].x-p[i].x)>0) mi=i; swap(p[0],p[mi]); tmp=p[0]; sort(p+1,p+n,cmp); int top=0; convex[top++]=p[0]; convex[top++]=p[1]; int k=2; while(k<=n){ while(top>=2 && sgn(cross(convex[top-2],p[k%n],convex[top-1]))>=0) top--; convex[top++]=p[k%n]; k++; } return top; } double pi=acos(-1.0);