zoukankan      html  css  js  c++  java
  • BZOJ 2829 凸包

    思路:

    把信用卡周围去掉  只剩下中间的长方形 

    最后的答案加上一个圆

    //By SiriusRen
    #include <bits/stdc++.h>
    using namespace std;
    const int N=50000;
    const double eps=1e-10;
    int card,n,m,k;
    double a,b,r,xx,yy,theta,Ans;
    struct Point{
        double x,y;Point(){}
        Point(double X,double Y){x=X,y=Y;}
    }point[N],tubao[N];
    bool cmp1(Point a,Point b){if(abs(a.x-b.x)>eps)return a.x<b.x;return a.y<b.y;}
    double cross(Point a,Point b,Point c){
        return (a.x-c.x)*(b.y-c.y)-(a.y-c.y)*(b.x-c.x);
    }
    double dis(Point a,Point b){
        return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));
    }
    int main(){
        scanf("%d%lf%lf%lf",&card,&a,&b,&r);
        Ans+=2*acos(-1)*r;
        a=a-2*r,b=b-2*r;
        for(int i=1;i<=card;i++){
            scanf("%lf%lf%lf",&xx,&yy,&theta);
            point[++n]=Point(xx-sin(theta)*a/2-cos(theta)*b/2,yy+cos(theta)*a/2-sin(theta)*b/2);
            point[++n]=Point(xx-sin(theta)*a/2+cos(theta)*b/2,yy+cos(theta)*a/2+sin(theta)*b/2);
            point[++n]=Point(xx+sin(theta)*a/2-cos(theta)*b/2,yy-cos(theta)*a/2-sin(theta)*b/2);
            point[++n]=Point(xx+sin(theta)*a/2+cos(theta)*b/2,yy-cos(theta)*a/2+sin(theta)*b/2);
        }
        sort(point+1,point+1+n,cmp1);
        for(int i=1;i<=n;i++){
            while(m>1&&cross(tubao[m],point[i],tubao[m-1])<eps)m--;
            tubao[++m]=point[i];
        }k=m;
        for(int i=n-1;i;i--){
            while(m>k&&cross(tubao[m],point[i],tubao[m-1])<eps)m--;
            tubao[++m]=point[i];
        }
        for(int i=1;i<m;i++)Ans+=dis(tubao[i],tubao[i+1]);
        printf("%.2lf
    ",Ans);
    }
  • 相关阅读:
    进程间通信(管道和有名管道)
    BAT面试需要什么样的程序员?
    深入剖析Redis系列: Redis哨兵模式与高可用集群
    七大进程间通信和线程同步
    详解Redis 的持久化机制--RDB和AOF
    大型网站技术架构演进
    Coding Standard(编程规范)
    @RequestBody,415Unsupported Media Type错误
    排序算法
    单例设计模式
  • 原文地址:https://www.cnblogs.com/SiriusRen/p/6908852.html
Copyright © 2011-2022 走看看