学习资料处

HDU 1542 Atlantis

题意:给出几个矩阵求这些矩阵覆盖的面积:

给出左上角与右下角

Sample Input

2
0 5 4 1
2 4 6 2

Sample Output

20

 

#include<bits/stdc++.h>
using namespace std;
#define LL long long
#define lson l, m, rt<<1
#define rson m+1,r,rt<<1|1
const int maxn = 5e3 + 10;
const int Base = 1e8;
LL sum[maxn<<2];
int add[maxn];
int x[maxn<<2];

struct Node{
    int flag;
    int l, r, h;
    Node(){};
    Node(int L, int R, int H, int F):l(L),r(R),h(H),flag(F){};
    bool operator < (const Node & rhs) const{
        return this->h < rhs.h;
    };
}s[maxn];
 void UPDOWN(int rt, int l, int r)
{
    if(add[rt]) sum[rt] = x[r+1] - x[l];

    else if(l == r) sum[rt] = 0;
    else sum[rt] = sum[rt<<1] + sum[rt<<1|1];
}
 void UPDATE(int L, int R, int c, int l, int r, int rt)
{
    int m;
    if(L <= l && r <= R){
        add[rt] += c;
        UPDOWN(rt, l, r);
        return ;
    }
    m = (l+r)>>1;
    if(L <= m) UPDATE(L, R, c, lson);
    if(R >  m) UPDATE(L, R, c, rson);
    UPDOWN(rt, l, r);
}

int main(void)
{
    int n;
    scanf("%d", &n);
    int x1, x2, y1, y2;
    int num = 0;
    for(int i=0; i<n; i++){
        scanf("%d %d %d %d", &x1, &y1, &x2, &y2);
        x1 += Base, x2 += Base, y1 += Base, y2 += Base;
        x[num] = x1;
        s[num++] = Node(x1, x2, y1, 1);
        x[num] = x2;
        s[num++] = Node(x1, x2, y2, -1);

    }
    sort(x, x+num);
    sort(s, s+num);
    int idx = std::unique(x, x+num) - x;
    int L, R;
    long long ans = 0;
    for(int i=0; i<num-1; i++){
        L = lower_bound(x, x+idx, s[i].l) - x;
        R = lower_bound(x, x+idx, s[i].r) - x - 1;
        UPDATE(L,R,s[i].flag,0,idx-1,1);
        ans+=(sum[1]*(1LL*s[i+1].h-1LL*s[i].h));
    }
    printf("%lld\n", ans);
    return 0;
}
View Code

 

给出左上角与右下角求矩阵的周长

 
 
#include<string.h>
#include<stdio.h>
#include<bits/stdc++.h>
#include<algorithm>
#define lson l, m, rt<<1
#define rson m+1,r,rt<<1|1
using namespace std;
const int maxn = 5010;
const int MAX  = 10010;
int add[2*MAX*4];
int sum[2*MAX*4];
struct Node{
    int flag;
    int l, r, h;
    Node(){};
    Node(int L, int R, int H):l(L),r(R),h(H){};
    bool operator < (const Node &rhs) const{
        if(this->h==rhs.h) return this->flag > rhs.flag;
        else return this->h < rhs.h;
    };
}sx[maxn<<1],sy[maxn<<1];

inline void Build(int l, int r, int rt)
{
    add[rt] = sum[rt] = 0;
    if(l >= r) return ;
    int m = l+((r-l)>>1);
    Build(lson);
    Build(rson);
}

inline void pushup(int rt, int l, int r)
{
    if(add[rt] > 0)    sum[rt] = r - l + 1;
    else if(l==r)      sum[rt] = 0;
    else               sum[rt] = sum[rt<<1] + sum[rt<<1|1];
}

inline void update(int L, int R, int c, int l, int r, int rt)
{
    int m;
    if(L <= l && r <= R){
        add[rt] += c;
        pushup(rt, l, r);
        return ;
    }
    m = l + ((r-l)>>1);
    if(L <= m) update(L, R, c, lson);
    if(R  > m) update(L, R, c, rson);
    pushup(rt, l, r);
}

int Solve(int minx, int maxx, int miny, int maxy, int num)
{
    int ret = 0;
    int pre = 0;
    Build(minx, maxx-1, 1);
    for(int i=0; i<num; i++){
        update(sx[i].l, sx[i].r-1, sx[i].flag, minx, maxx-1, 1);
        ret += abs(sum[1] - pre);
        pre = sum[1];
    }
    //printf("%d\n", ret);
    Build(miny, maxy-1, 1);
    pre = 0;
    for(int i=0; i<num; i++){
        update(sy[i].l, sy[i].r-1, sy[i].flag, miny, maxy-1, 1);
        ret += abs(sum[1] - pre);
        pre = sum[1];
    }
    return ret;
}

int main(void)
{
    //freopen("data1.in", "w", stdin);
    int n;
    while(~scanf("%d", &n)){
        int maxx, maxy, minx, miny;
        maxx = maxy = -0x3f3f3f3f;
        minx = miny =  0x3f3f3f3f;
        int x1, y1, x2, y2;
        int num = 0;
        for(int i=0; i<n; i++){
            scanf("%d %d %d %d", &x1,&y1,&x2,&y2);
            miny = min(y1, miny);
            minx = min(x1, minx);
            maxy = max(y2, maxy);
            maxx = max(x2, maxx);
            sx[num].l = x1, sx[num].r = x2, sx[num].h = y1, sx[num].flag = 1;
            sx[num+1].l=x1, sx[num+1].r=x2, sx[num+1].h=y2, sx[num+1].flag=-1;

            sy[num].l = y1, sy[num].r = y2, sy[num].h = x1, sy[num].flag = 1;
            sy[num+1].l=y1, sy[num+1].r=y2, sy[num+1].h=x2, sy[num+1].flag=-1;

            num+=2;
        }
        sort(sx, sx+num);
        sort(sy, sy+num);
        printf("%d\n", Solve(minx, maxx, miny, maxy, num));
    }
    return 0;
}
View Code

 

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

相关文章: