zoukankan      html  css  js  c++  java
  • bzoj2618 凸多边形 半平面交

    链接:http://www.lydsy.com/JudgeOnline/problem.php?id=2618

    题意:求出几个封闭图形围成的内部区域面积。

    把每一条边作为有向直线,逆时针遍历全图,左侧的半平面交

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cstring>
     4 #include<algorithm>
     5 #include<cmath>
     6 using namespace std;
     7 int n,cnt;
     8 const int maxn=55;
     9 struct point
    10 {
    11     double x,y;
    12 }p[maxn],a[maxn*maxn];
    13 double operator *(const point &a,const point &b)
    14 {
    15     return a.x*b.y-a.y*b.x;
    16 }
    17 point operator -(const point &a,const point &b)
    18 {
    19     return (point){a.x-b.x,a.y-b.y};
    20 }
    21 struct line
    22 {
    23     point a,b;double slop;
    24     friend bool operator <(const line &a,const line &b)
    25     {
    26         if(a.slop!=b.slop)return a.slop<b.slop;
    27         return (b.b-a.a)*(a.b-a.a)<0;
    28     }
    29     void print()
    30     {
    31         printf("%lf %lf %lf %lf
    ",a.x,a.y,b.x,b.y);
    32     }
    33 }l[maxn*maxn],q[maxn*maxn];
    34 void pre()
    35 {
    36     for(int i=1;i<=cnt;i++)l[i].slop=atan2(l[i].b.y-l[i].a.y,l[i].b.x-l[i].a.x);
    37     sort(l+1,l+cnt+1);int tot=0;
    38     for(int i=1;i<=cnt;i++)
    39     {
    40         if(l[i].slop!=l[i-1].slop)tot++;
    41         l[tot]=l[i];
    42     }
    43     cnt=tot;
    44 }
    45 point inter(line a,line b)
    46 {
    47     double k1,k2;
    48     k1=(a.a-b.a)*(a.a-b.b),k2=(a.b-b.b)*(a.b-b.a);
    49     k1=k1/(k1+k2);
    50     point ans;
    51     ans.x=a.a.x+k1*(a.b.x-a.a.x),ans.y=a.a.y+k1*(a.b.y-a.a.y);
    52     return ans;
    53 }
    54 bool judge(point a,line b)
    55 {
    56     return (b.a-a)*(b.b-a)<0;
    57 }
    58 void work()
    59 {
    60     int L=1,R=0;
    61     q[++R]=l[1],q[++R]=l[2];
    62     for(int i=3;i<=cnt;i++)
    63     {
    64         while(L<R&&judge(inter(q[R],q[R-1]),l[i]))R--;
    65         while(L<R&&judge(inter(q[L],q[L+1]),l[i]))L++;
    66         q[++R]=l[i];
    67     }
    68     while(L<R&&judge(inter(q[R],q[R-1]),q[L]))R--;
    69     cnt=0;
    70     for(int i=L;i<R;i++)a[++cnt]=inter(q[i],q[i+1]);
    71     a[++cnt]=inter(q[R],q[L]);
    72 }
    73 void getans()
    74 {
    75     double ans=0;
    76     for(int i=1;i<cnt;i++)ans+=a[i]*a[i+1];
    77     ans+=a[cnt]*a[1];
    78     ans=fabs(ans/2.0);
    79     printf("%0.3lf",ans);
    80 }
    81 int haha()
    82 {
    83     scanf("%d",&n);
    84     for(int i=1;i<=n;i++)
    85     {
    86         int m;scanf("%d",&m);
    87         for(int j=1;j<=m;j++)
    88         {
    89             scanf("%lf%lf",&p[j].x,&p[j].y);
    90             if(j==1)continue;
    91             l[++cnt].a=p[j-1];l[cnt].b=p[j];
    92         }
    93         l[++cnt].a=p[m];l[cnt].b=p[1];
    94     }
    95     pre();work();getans();
    96 }
    97 int sb=haha();
    98 int main(){;}
    bzoj2618

    就是所求的结果。

  • 相关阅读:
    【洛谷P1005】矩阵取数游戏
    【洛谷P1966】火柴排队
    【题解】洛谷P1731 [NOI1999] 生日蛋糕(搜索+剪枝)
    【题解】洛谷P3627 [APIO2009]抢掠计划(缩点+SPFA)
    【题解】洛谷P1262 间谍网络 (强连通分量缩点)
    【题解】洛谷P3200 [HNOI2009] 有趣的数列(卡特兰数+质因数分解)
    点双连通分量 [HNOI2012]矿场搭建
    分块 公主的朋友
    [置顶] 数学的坑,一点点来填
    大暴搜 [NOIP2009]靶形数独
  • 原文地址:https://www.cnblogs.com/Loser-of-Life/p/7291560.html
Copyright © 2011-2022 走看看