首页 > 代码库 > HDU1255【线段树+扫描线】

HDU1255【线段树+扫描线】

#include<iostream>#include<cstdio>#include<algorithm>using namespace std;#define L(k) k<<1#define R(k) k<<1|1const int NO=1005;struct X{    int l,r;    int s;}p[NO<<2];struct LINE{    double l,r;    double h;    int s;}line[NO<<1];int n,m;double sum;double x[NO<<1]={-1};bool H(const LINE &a,const LINE &b){return a.h<b.h;}void creat(int k,int l,int r){    p[k].l=l;    p[k].r=r;    p[k].s=0;    if(l==r)        return;    int mid=(l+r)>>1;    creat(L(k),l,mid);    creat(R(k),mid+1,r);}int s;void update(int k,double l,double r){    if(p[k].s!=-1&&x[p[k].l]==l&&x[p[k].r+1]==r)    {        if(p[k].s==2&&s==-1)            sum-=x[p[k].r+1]-x[p[k].l];        else if(p[k].s==1&&s==1)            sum+=x[p[k].r+1]-x[p[k].l];        p[k].s+=s;        return;    }    if(p[k].s!=-1)        p[L(k)].s=p[R(k)].s=p[k].s;    int mid=(p[k].l+p[k].r)>>1;    if(r<=x[mid+1])        update(L(k),l,r);    else if(x[mid+1]<=l)        update(R(k),l,r);    else    {        update(L(k),l,x[mid+1]);        update(R(k),x[mid+1],r);    }    p[k].s=p[L(k)].s==p[R(k)].s?p[L(k)].s:-1;}int main(){    freopen("1.txt","r",stdin);    int ttt;    scanf("%d",&ttt);    while(ttt--)    {        scanf("%d",&m);        for(int i=1;i<=m;i++)        {            scanf("%lf%lf%lf%lf",&x[i],&line[i].h,&x[m+i],&line[m+i].h);            line[i].l=line[m+i].l=x[i];            line[i].r=line[m+i].r=x[m+i];            line[i].s=1;            line[m+i].s=-1;        }        sort(x+1,x+2*m+1);        sort(line+1,line+2*m+1,H);        n=0;        for(int i=1;i<=2*m;i++)            if(x[i]!=x[i-1])                x[++n]=x[i];        creat(1,1,n-1);        double ans=sum=0;        line[0].h=line[1].h;        for(int i=1;i<=2*m;i++)        {            ans+=(line[i].h-line[i-1].h)*sum;            s=line[i].s;            update(1,line[i].l,line[i].r);        }        printf("%.2lf\n",ans);    }    return 0;}
View Code

 

HDU1255【线段树+扫描线】