覆盖的面积 HDU - 1255(扫描线进阶)
#include<cstdio>
#include<iostream>
#include<cmath>
#include<functional>
#include<cstring>
#include<string>
#include<cstdlib>
#include<queue>
#include<map>
#include<algorithm>
#include<set>
#include<vector>
#include<stack>
using namespace std;
typedef long long ll;
const int INF=0x3f3f3f;
int mod=1000000007;
const int N=2e3+10;
double v[N];
double ans;
struct L
{
double x,y1,y2;
int state;
} line[N];
struct node
{
double l,r;
int cover;
double len,len2;
} p[N<<3];
int ls(int k)
{
return k<<1;
}
int rs(int k)
{
return k<<1|1;
}
bool cmp(L a,L b)
{
return a.x<b.x;
}
void pushup(int k)
{
if(p[k].cover)p[k].len=p[k].r-p[k].l,p[k].len2=p[ls(k)].len+p[rs(k)].len;
else p[k].len=p[ls(k)].len+p[rs(k)].len,p[k].len2=p[ls(k)].len2+p[rs(k)].len2;
if(p[k].cover>1)p[k].len2=p[k].r-p[k].l;
else if(p[k].l==p[k].r)p[k].len2=0;
}
void build(int l,int r,int k)
{
p[k].l=v[l];
p[k].r=v[r];
if(r-l<=1)return ;
int mid=(l+r)/2;
build(l,mid,ls(k));
build(mid,r,rs(k));
}
void modify(double x,double y,int z,int k)
{
double l=p[k].l,r=p[k].r;
if(x<=l&&r<=y)
{
p[k].cover+=z;
pushup(k);
return ;
}
if(x<p[ls(k)].r)modify(x,y,z,ls(k));
if(y>p[rs(k)].l)modify(x,y,z,rs(k));
pushup(k);
}
int main()
{
int n;
int zhl;
scanf("%d",&zhl);
while(zhl--)
{
scanf("%d",&n);
double x1,x2,y1,y2;
ans=0.0;
for(int i=1;i<=2*n;i++)
{
v[i]=0.0;
p[i].l=p[i].r=p[i].len=0.0;
line[i].x=line[i].y1=line[i].y2=0.0;
}
for(int i=1; i<=n; i++)
{
scanf("%lf%lf%lf%lf",&x1,&y1,&x2,&y2);
if(x1>x2)swap(x1,x2);
if(y1>y2)swap(y1,y2);
line[i].x=x1;
line[i+n].x=x2;
line[i].y1=line[i+n].y1=y1;
line[i].y2=line[i+n].y2=y2;
line[i].state=1;
line[i+n].state=-1;
v[i]=y1;
v[i+n]=y2;
}
sort(v+1,v+2*n+1);
sort(line+1,line+2*n+1,cmp);
build(1,n*2,1);
for(int i=1; i<=n*2; i++)
{
ans+=p[1].len2*(line[i].x-line[i-1].x);
modify(line[i].y1,line[i].y2,line[i].state,1);
}
printf("%.2f\n",ans);
}
return 0;
}