啥都不会啊!怎么办啊!

Fitz

慢慢来生活总会好起来的!!!

覆盖的面积 HDU - 1255 (线段树-扫描线)模板提

给定平面上若干矩形,求出被这些矩形覆盖过至少两次的区域的面积. 

Input输入数据的第一行是一个正整数T(1<=T<=100),代表测试数据的数量.每个测试数据的第一行是一个正整数N(1<=N<=1000),代表矩形的数量,然后是N行数据,每一行包含四个浮点数,代表平面上的一个矩形的左上角坐标和右下角坐标,矩形的上下边和X轴平行,左右边和Y轴平行.坐标的范围从0到100000. 

注意:本题的输入数据较多,推荐使用scanf读入数据. 
Output对于每组测试数据,请计算出被这些矩形覆盖过至少两次的区域的面积.结果保留两位小数. 
Sample Input

2
5
1 1 4 2
1 3 3 7
2 1.5 5 4.5
3.5 1.25 7.5 4
6 3 10 7
3
0 0 1 1
1 0 2 1
2 0 3 1

Sample Output

7.63
0.00


这题是线段树扫描线水题

扫描线一开始以为特别难
但是用心去看还是比较容易的
试着用自己的方法理解
掌握思想

 1 #include <cstdio>
 2 #include <cstring>
 3 #include <algorithm>
 4 #include <cmath>
 5 #include <ctype.h>
 6 #include <set>
 7 #include <map>
 8 #include <queue>
 9 #include <stack>
10 #include <iostream>
11 using namespace std;
12 #define bug printf("******\n");
13 #define rtl  rt<<1
14 #define rtr  rt<<1|1
15 typedef long long LL;
16 const int maxn = 1e4 + 10;
17 struct LINE {
18     double x, y1, y2;
19     int flag;
20 } line[maxn];
21 int cmp(LINE a, LINE b) {
22     return a.x < b.x;
23 }
24 struct node {
25     double x, l, r, pre;
26     int flag, cover;
27 } tree[maxn << 2];
28 double y[maxn];
29 void build(int l, int r, int rt ) {
30     tree[rt].l = y[l], tree[rt].r = y[r];
31     tree[rt].pre = 0, tree[rt].cover = 0, tree[rt].flag = 0;
32     if (l + 1 == r) {
33         tree[rt].flag = 1;
34         return ;
35     }
36     int m = (l + r) >> 1;
37     build(l, m, rtl);
38     build(m, r, rtr);
39 }
40 double query(int rt, double x, double y1, double y2, int flag) {
41     if (tree[rt].l >= y2 || tree[rt].r <= y1) return 0;
42     if (tree[rt].flag == 1) {
43         if (tree[rt].cover > 1) {
44             double pre = tree[rt].pre;
45             double ans = (x - pre) * (tree[rt].r - tree[rt].l);
46             tree[rt].pre = x;
47             tree[rt].cover += flag;
48             return ans;
49         } else {
50             tree[rt].cover += flag;
51             tree[rt].pre = x;
52             return 0;
53         }
54     }
55     return query(rtl, x, y1, y2, flag) + query(rtr, x, y1, y2, flag);
56 }
57 int main() {
58     int t, n;
59     scanf("%d", &t);
60     while(t--) {
61         scanf("%d", &n);
62         int cnt = 0;
63         for (int i = 0 ; i < n ; i++) {
64             double x1, y1, x2, y2;
65             scanf("%lf%lf%lf%lf", &x1, &y1, &x2, &y2);
66             y[cnt] = y1;
67             line[cnt].x = x1;
68             line[cnt].y1 = y1;
69             line[cnt].y2 = y2;
70             line[cnt++].flag = 1;
71             y[cnt] = y2;
72             line[cnt].x = x2;
73             line[cnt].y1 = y1;
74             line[cnt].y2 = y2;
75             line[cnt++].flag = -1;
76         }
77         sort(y, y + cnt );
78         sort(line, line + cnt, cmp);
79         build(0, cnt-1, 1);
80         double ans = 0;
81         for (int i = 0 ; i < cnt ; i++)
82             ans += query(1, line[i].x, line[i].y1, line[i].y2, line[i].flag);
83         printf("%.2f\n", ans);
84     }
85     return 0;
86 }

 

posted @ 2018-07-29 23:01  Fitz~  阅读(309)  评论(0编辑  收藏  举报