/*
在这里将一个一个的矩形分隔成两条平行X轴的线,
在下面一条标记为正边,上面一条标记为负边。
cnt表示的次节点被覆盖的次数。
sum表示区间一次覆盖以上的长度
len表示区间二次覆盖以上的长度
*/
#include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstring>
using namespace std;
#define maxn 2222
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define mid (l+r)>>1
double X[maxn<<2],sum[maxn<<2],len[maxn<<2];
int cnt[maxn<<2];
struct Seg{
double l,r,h;
int c;
Seg(){};
Seg(double t1,double t2,double t3,int t4) :l(t1),r(t2),h(t3),c(t4){}
bool operator < (Seg& cmp){
return h<cmp.h;
}
}seg[maxn<<2];
void Pushup(int l,int r,int rt){
if(cnt[rt])
sum[rt] = X[r+1]-X[l];//实际长度时往开区间移
else if(l == r)
sum[rt] = 0;
else
sum[rt] = sum[rt<<1]+sum[rt<<1|1];
}
void Pushupagain(int l,int r,int rt){
if(cnt[rt]>=2) //如果已经两次以上被覆盖,即为交集
len[rt] = X[r+1] -X[l];
else if(l == r)//叶子节点长度为0
len[rt] = 0;
else if(cnt[rt] == 1)//如果覆盖线段为1,那么等于已经覆盖的左右子树的长度和
len[rt] = sum[rt<<1] +sum[rt<<1|1];
else //否则等于已经覆盖的左右子树长度和。
len[rt] = len[rt<<1] + len[rt<<1|1];
}
int Bin(double key,int n){
return lower_bound(X,X+n,key)-X;
}
void Update(int L,int R,int c,int l,int r,int rt){
if(L<=l && r<=R){
cnt[rt]+=c;
Pushup(l,r,rt);
Pushupagain(l,r,rt);
return ;
}
int m=mid;
if(m>=L)
Update(L,R,c,lson);
if(m<R)
Update(L,R,c,rson);
Pushup(l,r,rt);
Pushupagain(l,r,rt);
}
int main(){
int t,i,j,T;
scanf("%d",&T);
while(T--){
scanf("%d",&t);
double a[4];
int n=0;
for(i=0;i<t;i++){
for(j=0;j<4;j++)
scanf("%lf",&a[j]);
seg[n]=Seg(a[0],a[2],a[1],1);
X[n++]=a[0];
seg[n]=Seg(a[0],a[2],a[3],-1);
X[n++]=a[2];
}
sort(seg,seg+n);
sort(X,X+n);
int k=1;
for(i=1;i<n;i++){ //去重离散化
if(X[i-1]!=X[i])
X[k++]=X[i];
}
memset(cnt,0,sizeof(cnt));
memset(sum,0,sizeof(sum));
memset(len,0,sizeof(len));
double area=0,sre=0;
for(i=0;i<n-1;i++){
int l=Bin(seg[i].l,k);
int r=Bin(seg[i].r,k)-1; //左闭右开区间,取实区时往后移一个
if(l<=r)
Update(l,r,seg[i].c,0,k-1,1);
area+=len[1]*(seg[i+1].h-seg[i].h);
//sre+=sum[1]*(seg[i+1].h-seg[i].h);
}
// printf("Test case #%d\nTotal explored area: %.2lf\n\n",++cas,area);
printf("%.2lf\n",area);
//area 为面积交,sre为面积并
}
return 0;
}
hdu 1542 ,1255 线段树面积并与面积交
最新推荐文章于 2019-12-18 18:34:51 发布