zoukankan      html  css  js  c++  java
  • 【BZOJ1645】[Usaco2007 Open]City Horizon 城市地平线 离散化+线段树

    【BZOJ1645】[Usaco2007 Open]City Horizon 城市地平线

    Description

    Farmer John has taken his cows on a trip to the city! As the sun sets, the cows gaze at the city horizon and observe the beautiful silhouettes formed by the rectangular buildings. The entire horizon is represented by a number line with N (1 <= N <= 40,000) buildings. Building i's silhouette has a base that spans locations A_i through B_i along the horizon (1 <= A_i < B_i <= 1,000,000,000) and has height H_i (1 <= H_i <= 1,000,000,000). Determine the area, in square units, of the aggregate silhouette formed by all N buildings.

    N个矩形块,交求面积并.

    Input

    * Line 1: A single integer: N

    * Lines 2..N+1: Input line i+1 describes building i with three space-separated integers: A_i, B_i, and H_i

    Output

    * Line 1: The total area, in square units, of the silhouettes formed by all N buildings

    Sample Input

    4
    2 5 1
    9 10 4
    6 8 2
    4 6 3

    Sample Output

    16

    OUTPUT DETAILS:

    The first building overlaps with the fourth building for an area of 1
    square unit, so the total area is just 3*1 + 1*4 + 2*2 + 2*3 - 1 = 16.

    题解:一看就是离散化+线段树的题,可以先将h离散,再按a,b排序,用线段树维护扫描线来做,不过这样比较麻烦。

    因为本题中所有的矩形底边都在同一直线上,所以我们可以把这些矩形整体看成一棵线段树,线段树的区间就是每个a,b,线段树的权值就是h,然后按h排序,从小到大一个一个加到线段树里就行了。

    注意:a和b离散化后是2*40000的空间,所以线段树要开8*40000!2*4==8!!!

    #include <cstdio>
    #include <cstring>
    #include <iostream>
    #include <algorithm>
    #define lson x<<1
    #define rson x<<1|1
    using namespace std;
    const int maxn=40010;
    typedef long long ll;
    struct edges
    {
        ll pos,org;
    }s[maxn<<1];
    struct house
    {
        ll sa,sb,sh;
    }p[maxn];
    int n,m;
    ll ts[maxn<<3],tag[maxn<<3],ref[maxn<<1];
    bool cmp1(edges a,edges b)
    {
        return a.pos<b.pos;
    }
    bool cmp2(house a,house b)
    {
        return a.sh<b.sh;
    }
    void pushdown(int l,int r,int x)
    {
        if(tag[x])
        {
            int mid=l+r>>1;
            ts[lson]=(ref[mid]-ref[l])*tag[x],ts[rson]=(ref[r]-ref[mid])*tag[x];
            tag[lson]=tag[rson]=tag[x];
            tag[x]=0;
        }
    }
    void pushup(int x)
    {
        ts[x]=ts[lson]+ts[rson];
    }
    void updata(int l,int r,int x,int a,int b,ll v)
    {
        if(a<=l&&r<=b)
        {
            ts[x]=(ref[r]-ref[l])*v;
            tag[x]=v;
            return ;
        }
        pushdown(l,r,x);
        int mid=l+r>>1;
        if(b<=mid)    updata(l,mid,lson,a,b,v);
        else if(a>=mid)    updata(mid,r,rson,a,b,v);
        else    updata(l,mid,lson,a,b,v),updata(mid,r,rson,a,b,v);
        pushup(x);
    }
    int main()
    {
        scanf("%d",&n);
        int i;
        for(i=1;i<=n;i++)
        {
            scanf("%lld%lld%lld",&p[i].sa,&p[i].sb,&p[i].sh);
            s[i*2-1].pos=p[i].sa,s[i*2].pos=p[i].sb;
            s[i*2-1].org=s[i*2].org=i;
        }
        sort(s+1,s+2*n+1,cmp1);
        for(i=1;i<=2*n;i++)
        {
            if(s[i].pos>ref[m])    ref[++m]=s[i].pos;
            if(s[i].pos==p[s[i].org].sa)    p[s[i].org].sa=m;
            else    p[s[i].org].sb=m;
        }
        sort(p+1,p+n+1,cmp2);
        for(i=1;i<=n;i++)
            updata(1,m,1,p[i].sa,p[i].sb,p[i].sh);
        printf("%lld",ts[1]);
        return 0;
    }
  • 相关阅读:
    char varchar nchar nvarchar text ntext区别
    Bindable 使用
    ShareObject离线存储相关
    as CPU 优化【转】
    as类收集(转)
    TweenLite 使用简介
    34个有用的ActionScript 3.0的API【转】
    as类库
    【转】A*寻路
    IOS学习笔记34—EGOTableViewPullRefresh实现下拉刷新
  • 原文地址:https://www.cnblogs.com/CQzhangyu/p/6281746.html
Copyright © 2011-2022 走看看