[SHOI2012] convex hull credit card

topic

For a smooth rectangular treated, we find that its perimeter is four \ (\ frac {1} { 4} \) rectangular circumference of a circle center formed on the circumference of a circle plus

So we strongly suspect that the answer is to put all \ (\ frac {1} { 4} \) center of the circle to win to build a convex hull, on the perimeter of the convex hull of a circle's circumference to plus; find this very correct, emotional understanding of what is probably the convex polygon turned a \ (2 \ PI \) , so that each arc and a complete circle

So now the board becomes a problem, the code

#include<bits/stdc++.h>
#define re register
#define sqr(x) ((x)*(x))
#define double long double
#define cK ((p[i]-st[top-1])*(st[top]-st[top-1]))
const int maxn=5e4+5;
const double eps=1e-7;
const double pi=acos(-1);
int top,n,N;
struct pt{double x,y;}p[maxn],st[maxn];
inline int dcmp(double a,double b) {return a+eps>b&&a-eps<b;}
inline double operator*(const pt &A,const pt &B) {return A.x*B.y-A.y*B.x;}
inline pt operator+(const pt &A,const pt &B) {return (pt){A.x+B.x,A.y+B.y};}
inline pt operator-(const pt &A,const pt &B) {return (pt){A.x-B.x,A.y-B.y};}
inline double dis(const pt &A,const pt &B) {return sqrt(sqr(A.x-B.x)+sqr(A.y-B.y));}
inline double size(const pt &A) {return dis((pt){0,0},A);}
inline pt rotate(const pt &O,const pt &A,double det) {
    pt B;B=A-O;double c=cos(det),s=sin(det);
    return O+(pt){B.x*c-B.y*s,B.x*s+B.y*c};
}
inline int cmp(const pt &A,const pt &B) {
    double t=A*B;
    return dcmp(t,0)?size(A)<size(B):(t>0);
}
int main() {
    //freopen("data.in","r",stdin);
    double a,b,det;pt nw,o;double A,B,r;
    scanf("%d%Lf%Lf%Lf",&n,&B,&A,&r);A*=0.5,B*=0.5;
    for(re int i=1;i<=n;i++) {
        scanf("%Lf%Lf%Lf",&a,&b,&det);o.x=a,o.y=b;
        nw.x=a-A+r,nw.y=b+B-r;
        p[++N]=rotate(o,nw,det);
        nw.x=a+A-r,nw.y=b+B-r;
        p[++N]=rotate(o,nw,det);
        nw.x=a-A+r,nw.y=b-B+r;
        p[++N]=rotate(o,nw,det);
        nw.x=a+A-r,nw.y=b-B+r;
        p[++N]=rotate(o,nw,det);
    }
    //for(re int i=1;i<=N;i++) printf("%.4Lf %.4Lf\n",p[i].x,p[i].y);puts("");
    pt S;S=p[1];
    for(re int i=2;i<=N;i++)
        if(p[i].x<S.x) S=p[i];else if(dcmp(p[i].x,S.x)&&p[i].y<S.y) S=p[i];
    for(re int i=1;i<=N;i++) p[i]=p[i]-S;
    std::sort(p+1,p+N+1,cmp);
    for(re int i=1;i<=N;++i) {
        while(top>1&&(cK>0||dcmp(cK,0))) --top;
        st[++top]=p[i];
    }
    st[top+1]=st[1];double ans=2.0*pi*r;
    for(re int i=1;i<=top;i++) ans+=dis(st[i],st[i+1]);
    printf("%.2Lf\n",ans);return 0;
}
//g++ lg3829.cpp -o lg3829

Guess you like

Origin www.cnblogs.com/asuldb/p/12169457.html