poj 1151 http://poj.org/problem?id=1151

大神orz

这是弱渣扫面线第一题,感觉区域赛有比较多的用的这个思想,所以赶在区域赛前熟悉一下扫描线和线段树(学习经验就是看着代码,然后一步一步测试,差不多就明白了

 

/**************************************************************
    Problem:poj 1151
    User: youmi
    Language: C++
    Result: Accepted
    Time:0MS
    Memory:740K
****************************************************************/
//#pragma comment(linker, "/STACK:1024000000,1024000000")
//#include<bits/stdc++.h>
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <map>
#include <stack>
#include <set>
#include <sstream>
#include <cmath>
#include <queue>
#include <deque>
#include <string>
#include <vector>
#define zeros(a) memset(a,0,sizeof(a))
#define ones(a) memset(a,-1,sizeof(a))
#define sc(a) scanf("%d",&a)
#define sc2(a,b) scanf("%d%d",&a,&b)
#define sc3(a,b,c) scanf("%d%d%d",&a,&b,&c)
#define scs(a) scanf("%s",a)
#define sclld(a) scanf("%I64d",&a)
#define pt(a) printf("%d\n",a)
#define ptlld(a) printf("%I64d\n",a)
#define rep0(i,n) for(int i=0;i<n;i++)
#define rep1(i,n) for(int i=1;i<=n;i++)
#define rep_1(i,n) for(int i=n;i>=1;i--)
#define rep_0(i,n) for(int i=n-1;i>=0;i--)
#define Max(a,b) ((a)>(b)?(a):(b))
#define Min(a,b) ((a)<(b)?(a):(b))
#define lson (step<<1)
#define rson (lson+1)
#define esp 1e-6
#define oo 0x3fffffff
#define TEST cout<<"*************************"<<endl

using namespace std;
typedef long long ll;

int n;
const int maxn=1000;
double x[maxn];
struct node
{
    double xl,xr,y,s;
    node(){}
    node(double _xl,double _xr,double _y,double _s)
    {
        xl=_xl,xr=_xr,y=_y,s=_s;
    }
    bool operator<(const node & b)const
    {
        return y<b.y;
    }
}line[maxn];
struct Seg
{
    int l,r,flag;
    double sum;
    Seg(){}
    Seg(int _l,int _r,int _flag,double _sum)
    {
        l=_l,r=_r,flag=_flag,sum=_sum;
    }
}seg[maxn];
int sgn(double x0)
{
    if(fabs(x0)<esp)
        return 0;
    if(x0<0)
        return -1;
    else
        return 1;
}
int bs(double x0)
{
    int l=1,r=n;
    while(l<=r)
    {
        int mid=(l+r)>>1;
        if(sgn(x0-x[mid])==0)
            return mid;
        if(sgn(x0-x[mid])==1)
            l=mid+1;
        else
            r=mid-1;
    }
}
void pushup(int step)
{
    if(seg[step].flag)
        seg[step].sum=x[seg[step].r+1]-x[seg[step].l];
    else if(seg[step].l==seg[step].r)
        seg[step].sum=0;
    else
        seg[step].sum=seg[lson].sum+seg[rson].sum;
}
void build(int step,int l,int r)
{
    seg[step]=Seg(l,r,0,0);
    if(l==r)
        return ;
    int mid=(l+r)>>1;
    build(lson,l,mid);
    build(rson,mid+1,r);
}
void update(int step,int l,int r,int val)
{
    if(seg[step].l==l&&seg[step].r==r)
    {
        seg[step].flag+=val;
        pushup(step);
        return;
    }
    int mid=(seg[step].l+seg[step].r)>>1;
    if(mid>=r)
        update(lson,l,r,val);
    else if(mid<l)
        update(rson,l,r,val);
    else
    {
        update(lson,l,mid,val);
        update(rson,mid+1,r,val);
    }
    pushup(step);
}
int main()
{
    //freopen("in.txt","r",stdin);
    int kase=0;
    while(~sc(n)&&n)
    {
        if(kase)
            cout<<endl;
        double x1,y1,x2,y2;
        int cnt=0;
        for(int i=1;i<=n;i++)
        {
            scanf("%lf%lf%lf%lf",&x1,&y1,&x2,&y2);
            line[cnt++]=node(x1,x2,y1,1);
            x[cnt]=x1;
            line[cnt++]=node(x1,x2,y2,-1);
            x[cnt]=x2;
        }
        sort(x+1,x+cnt+1);
        sort(line,line+cnt);
        n=1;
        for(int i=2;i<=cnt;i++)
            if(x[i]!=x[i-1])
                x[++n]=x[i];
        build(1,1,n);
        double ans=0;
        for(int i=0;i<cnt-1;i++)
        {
            int l=bs(line[i].xl);
            int r=bs(line[i].xr)-1;
            update(1,l,r,line[i].s);
            ans+=seg[1].sum*(line[i+1].y-line[i].y);
        }
        printf("Test case #%d\n",++kase);
        printf("Total explored area: %.2f \n",ans);
    }
    return 0;
}

 

posted on 2015-11-17 11:42  中子星  阅读(218)  评论(0编辑  收藏  举报