[HDU1255]覆盖的面积

Description:

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

Hint:

\(n\le 1000\)

Solution:

扫描线push_up时多讨论几种情况而已

#include <map>
#include <set>
#include <stack>
#include <cmath>
#include <queue>
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <iostream>
#include <algorithm>
#define ls p<<1 
#define rs p<<1|1
using namespace std;
typedef long long ll;
const int mxn=1e5+5;
int n,m,tot,cnt,hd[mxn];
double tr[mxn<<2][2];
int cov[mxn<<2];
double x[mxn];

inline int read() {
    char c=getchar(); int x=0,f=1;
    while(c>'9'||c<'0') {if(c=='-') f=-1;c=getchar();}
    while(c<='9'&&c>='0') {x=(x<<3)+(x<<1)+(c&15);c=getchar();}
    return x*f;
}
inline void chkmax(int &x,int y) {if(x<y) x=y;}
inline void chkmin(int &x,int y) {if(x>y) x=y;}

struct T {
    double l,r,h; int val;
    friend bool operator < (T x,T y) {
        return x.h<y.h;
    }
}t[mxn];

void push_up(int p,int l,int r) {
    if(cov[p]>1) tr[p][0]=tr[p][1]=x[r+1]-x[l];
	else if(cov[p]==1){
		tr[p][0]=x[r+1]-x[l];
		if(l==r) tr[p][1]=0;
		else tr[p][1]=tr[ls][0]+tr[rs][0];
	}
	else if(l==r) tr[p][0]=tr[p][1]=0;
	else {
		tr[p][0]=tr[ls][0]+tr[rs][0];
		tr[p][1]=tr[ls][1]+tr[rs][1];
	}
}

void update(int l,int r,int ql,int qr,int val,int p) {
    if(ql<=l&&r<=qr) {
        cov[p]+=val;
        push_up(p,l,r);
        return ;
    } 
    int mid=(l+r)>>1;
    if(ql<=mid) update(l,mid,ql,qr,val,ls);
    if(qr>mid) update(mid+1,r,ql,qr,val,rs);
    push_up(p,l,r);
}

int main()
{
    int cas=1; cas=read();
    while(cas--) {
		n=read();
        if(n==0) break;
        cnt=tot=0; 
        for(int i=1;i<=n;++i) {
            double a,b,c,d;
            scanf("%lf%lf%lf%lf",&a,&b,&c,&d);
            t[++cnt]=(T){a,c,b,1}; x[cnt]=a;
            t[++cnt]=(T){a,c,d,-1}; x[cnt]=c;
        }
        sort(x+1,x+cnt+1);
        sort(t+1,t+cnt+1);
        ++tot;
        for(int i=2;i<=cnt;++i) 
            if(x[i]!=x[i-1]) x[++tot]=x[i];
        memset(tr,0,sizeof(tr));
        memset(cov,0,sizeof(cov));
        double ans=0;
        for(int i=1;i<cnt;++i) {
            int l=lower_bound(x+1,x+tot+1,t[i].l)-x;
            int r=lower_bound(x+1,x+tot+1,t[i].r)-x-1;
            update(1,tot,l,r,t[i].val,1);
            ans+=tr[1][1]*(t[i+1].h-t[i].h);
        }
        printf("%.2lf\n",ans);
    }
    return 0;
}
posted @ 2019-03-28 15:46  cloud_9  阅读(117)  评论(0编辑  收藏  举报