HDU 3265 Posters (线段树+扫描线)(面积并)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3265

给你n个中间被挖空了一个矩形的中空矩形,让你求他们的面积并。

其实一个中空矩形可以分成4个小的矩形,然后就是面积并,特别注意的是x1 == x3 || x2 == x4的时候,要特判一下,否则会RE。

  1 #include <iostream>
  2 #include <cstring>
  3 #include <cstdio>
  4 #include <algorithm>
  5 using namespace std;
  6 const int MAXN = 2e5 + 10;
  7 typedef long long LL;
  8 struct data {
  9     LL l , r , y , flag;
 10     bool operator <(const data& cmp) const {
 11         return y < cmp.y;
 12     }
 13 }a[MAXN << 3];
 14 struct segtree {
 15     LL val , l , r , add;
 16 }T[MAXN << 3];
 17 
 18 void build(int p , int l , int r) {
 19     int mid = (l + r) >> 1;
 20     T[p].l = l , T[p].r = r , T[p].val = T[p].add = 0;
 21     if(r - l == 1) {
 22         return ;
 23     }
 24     build(p << 1 , l , mid);
 25     build((p << 1)|1 , mid , r);
 26 }
 27 
 28 void pushup(int p) {
 29     if(T[p].add) {
 30         T[p].val = T[p].r - T[p].l;
 31     }
 32     else if(T[p].r - T[p].l == 1){
 33         T[p].val = 0;
 34     }
 35     else {
 36         T[p].val = T[p << 1].val + T[(p << 1)|1].val;
 37     }
 38 }
 39 
 40 void updata(int p , int l , int r , int add) {
 41     int mid = (T[p].l + T[p].r) >> 1;
 42     if(T[p].l == l && T[p].r == r) {
 43         T[p].add += add;
 44         pushup(p);
 45         return ;
 46     }
 47     if(r <= mid) {
 48         updata(p << 1 , l , r , add);
 49     }
 50     else if(l >= mid) {
 51         updata((p << 1)|1 , l , r , add);
 52     }
 53     else {
 54         updata(p << 1 , l , mid , add);
 55         updata((p << 1)|1 , mid , r , add);
 56     }
 57     pushup(p);
 58 }
 59 
 60 int main()
 61 {
 62     int n;
 63     LL x[8] , y[8];
 64     while(~scanf("%d" , &n) && n) {
 65         int f = 0;
 66         for(int i = 0 ; i < n ; i++) {
 67             for(int j = 1 ; j <= 4 ; j++) {
 68                 scanf("%lld %lld" , x + j , y + j);
 69             }
 70             sort(x + 1 , x + 5);
 71             sort(y + 1 , y + 5);
 72             a[f].l = x[1] , a[f].r = x[4] , a[f].y = y[4] , a[f].flag = -1;
 73             f++;
 74             a[f].l = x[1] , a[f].r = x[4] , a[f].y = y[3] , a[f].flag = 1;
 75             f++;
 76             a[f].l = x[1] , a[f].r = x[4] , a[f].y = y[2] , a[f].flag = -1;
 77             f++;
 78             a[f].l = x[1] , a[f].r = x[4] , a[f].y = y[1] , a[f].flag = 1;
 79             f++;
 80 
 81             a[f].l = x[1] , a[f].r = x[2] , a[f].y = y[3] , a[f].flag = -1;
 82             f++;
 83             a[f].l = x[1] , a[f].r = x[2] , a[f].y = y[2] , a[f].flag = 1;
 84             f++;
 85             a[f].l = x[3] , a[f].r = x[4] , a[f].y = y[3] , a[f].flag = -1;
 86             f++;
 87             a[f].l = x[3] , a[f].r = x[4] , a[f].y = y[2] , a[f].flag = 1;
 88             f++;
 89         }
 90         sort(a , a + f);
 91         LL res = 0;
 92         build(1 , 0 , 2e5 + 2);
 93         //注意l == r的特殊情况
 94         if(a[0].l != a[0].r)
 95             updata(1 , a[0].l , a[0].r , a[0].flag);
 96         for(int i = 1 ; i < f ; i++) {
 97             res += (a[i].y - a[i - 1].y) * T[1].val;
 98             if(a[i].r > a[i].l)
 99                 updata(1 , a[i].l , a[i].r , a[i].flag);
100         }
101         printf("%lld\n" , res);
102     }
103 }

 

posted @ 2016-04-28 22:57  Recoder  阅读(227)  评论(0编辑  收藏  举报