• poj 1151 线段树+扫描线


    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
    ",a)
    #define ptlld(a) printf("%I64d
    ",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
    ",++kase);
            printf("Total explored area: %.2f 
    ",ans);
        }
        return 0;
    }
    不为失败找借口,只为成功找方法
  • 相关阅读:
    上周热点回顾(11.1611.22)
    程序员求职招聘专题上线了
    上海地铁爱知书店博客园专柜
    上周热点回顾(11.911.15)
    求职与简历功能上线测试
    上周热点回顾(11.2311.29)
    软件工程:软件测试
    [文摘20100706]几种Web服务器比较 (Apache、IIS、Lighttpd、Nginx、LiteSpeed、Zeus)
    [转]CMMI的5个级别和25个过程域
    网上进销存几个参考网站
  • 原文地址:https://www.cnblogs.com/youmi/p/4971226.html
Copyright © 2020-2023  润新知