| Time Limit: 2 second(s) | Memory Limit: 64 MB |
Given some axis parallel rectangles, you have to find the union of their area. For example, see the shaded regions in the picture. Each rectangle will be denoted by four integers. They are x1, y1, x2, y2 where(x1, y1) denotes the lower left corner and (x2, y2) denotes the upper right corner.
For the picture above, there are three rectangles. For the yellow rectangle the co-ordinates are (0, 2) and (3, 6). For the blue rectangle the co-ordinates are (1, 3) and (6, 7). For the green rectangle the co-ordinates are (2, 1) and (5, 4). So, the union area is (the shaded region) 31 square units.
Input
Input starts with an integer T (≤ 13), denoting the number of test cases.
Each case starts with a line containing an integer n (1 ≤ n ≤ 30000). Each of the next n lines will contain four integers x1, y1, x2, y2 (0 ≤ x1, y1, x2, y2 ≤ 109, x1 < x2, y1 < y2) denoting a rectangle.
Output
For each case, print the case number and the union area.
Sample Input |
Output for Sample Input |
|
2 3 0 2 3 6 1 3 6 7 2 1 5 4 2 0 0 4 4 1 1 2 5 |
Case 1: 31 Case 2: 17 |
Notes
Dataset is huge, use faster I/O methods.
这题是经典矩形面积并。
所谓的矩形面积并,既在二维平面上,有很多个矩形,要求你求出他们的总面积(相交部分只算一次)。
普通方法容易出错,而且复杂度大。
此题的经典做法为线段树+扫描线。
模拟一条扫描线,扫描X轴,然后,用线段树维护线段总边长,通过sum*h既可算出矩形面积。
1 #include<iostream> 2 #include<cstring> 3 #include<cstdio> 4 #include<queue> 5 #include<algorithm> 6 using namespace std; 7 8 #define N 100010 9 #define lson l,mid,p<<1 10 #define rson mid+1,r,p<<1|1 11 #define demid int mid=(l+r)>>1 12 #define ll long long 13 ll segt[N<<2],col[N<<2]; 14 struct node{ 15 ll x1,x2; 16 ll y; 17 int flag; 18 node(){}; 19 node(ll _x1,ll _x2,ll _y,ll _flag){ 20 x1=_x1,x2=_x2,y=_y,flag=_flag; 21 }; 22 bool operator < (const node & a)const{ 23 return y<a.y; 24 }; 25 }pnt[N]; 26 int n,m; 27 ll x[N<<1]; 28 29 void pushup(int l,int r,int p){ 30 if(col[p]) segt[p]=x[r]-x[l-1]; 31 else segt[p]=segt[p<<1]+segt[p<<1|1]; 32 //printf("%d %d %d %d %d %d %d\n",segt[p<<1],segt[p<<1|1],col[p],l,r,p,segt[p]); 33 } 34 35 void update(int L,int R,int key,int l,int r,int p){ 36 if(L<=l && r<=R){ 37 col[p]+=key; 38 pushup(l,r,p); 39 return; 40 } 41 demid; 42 if(L<=mid) update(L,R,key,lson); 43 if(mid<R) update(L,R,key,rson); 44 pushup(l,r,p); 45 } 46 47 int main(){ 48 int t,cas=1; 49 cin>>t; 50 while(t--){ 51 cin>>n; 52 m=0; 53 for(int i=0;i<n;i++){ 54 int x1,y1,x2,y2; 55 scanf("%lld%lld%lld%lld",&x1,&y1,&x2,&y2); 56 x[m++]=x1; 57 x[m++]=x2; 58 pnt[i<<1]=node(x1,x2,y1,1); 59 pnt[i<<1|1]=node(x1,x2,y2,-1); 60 } 61 sort(pnt,pnt+2*n); 62 sort(x,x+m); 63 m=unique(x,x+m)-x; 64 memset(segt,0,sizeof(segt)); 65 memset(col,0,sizeof(col)); 66 ll res=0; 67 for(int i=0;i<2*n-1;i++){ 68 int l=lower_bound(x,x+m,pnt[i].x1)-x+1,r=lower_bound(x,x+m,pnt[i].x2)-x; 69 if(l<=r) update(l,r,pnt[i].flag,0,m+10,1); 70 res+=(pnt[i+1].y-pnt[i].y)*segt[1]; 71 //printf("%d %d %d %d %d= =\n",pnt[i].x1,pnt[i].x2,pnt[i].y,segt[1],res); 72 } 73 printf("Case %d: %lld\n",cas++,res); 74 } 75 return 0; 76 }
浙公网安备 33010602011771号