• [USACO 3.1.4] rect1(漂浮法)


    N(1 ≤ N ≤ 1,000)个不同颜色的不透明矩形被摆放在了一个白色的宽A高B(1 ≤ A,B ≤ 10,000)的网格上,矩形的边与网格的边平行。所有的长方形都放置在网格内,所以我们会看到不同形状的各种颜色。

    坐标系统的原点(0,0)设在这张白纸的左下角,而坐标轴则平行于网格边缘。求最后能看到的颜色,以及各颜色所占面积。

    输入:
    第1 行包含三个整数A、B 和N,由空格分开。
    第2 到N+1 行,每行五个整数:llx, lly, urx, ury, color,分别表示一个长方形的左下角坐标,右上角坐标和颜色。颜色1 和底部白纸的颜色相同(1 ≤ color ≤2,500)。矩形在输入文件中出现的顺序即为放置的先后顺序。

    这道题用到的方法叫做漂浮法

    想象一下,矩形倒序从水底一个一个地浮上来,如果遇到上面有东西的部分就停住,没有被挡住的地方继续上浮...

    如何实现?

    用一个变量记录当前浮到第几层,找到它上面第一个有交集的,分成四部分继续递归。

    分成四部分的时候,每查完一个要改一下当前边界。

    核心代码:

    (F = Floor,C = Ceil)

    int dfs(int L,int R,int F,int C,int k) {
        while(k <= n && (L >= r[k].x2 || R <= r[k].x1 || F >= r[k].y2 || C <= r[k].y1))
            k++;
        if(k > n) return (R-L)*(C-F);
        int sum = 0;
        if(L < r[k].x1) sum += dfs(L,r[k].x1,F,C,k+1), L = r[k].x1;
        if(R > r[k].x2) sum += dfs(r[k].x2,R,F,C,k+1), R = r[k].x2;
        if(F < r[k].y1) sum += dfs(L,R,F,r[k].y1,k+1), F = r[k].y1;
        if(C > r[k].y2) sum += dfs(L,R,r[k].y2,C,k+1), C = r[k].y2;
        return sum;
    }

    代码如下

    #include<cstdio>
    #include<iostream>
    #include<cmath>
    #include<cstring>
    #define MogeKo qwq
    using namespace std;
    
    const int maxn = 2505;
    int a,b,n,ans[maxn];
    
    struct rec {
        int x1,x2,y1,y2,col;
    } r[maxn];
    
    
    int dfs(int L,int R,int F,int C,int k) {
        while(k <= n && (L >= r[k].x2 || R <= r[k].x1 || F >= r[k].y2 || C <= r[k].y1))
            k++;
        if(k > n) return (R-L)*(C-F);
        int sum = 0;
        if(L < r[k].x1) sum += dfs(L,r[k].x1,F,C,k+1), L = r[k].x1;
        if(R > r[k].x2) sum += dfs(r[k].x2,R,F,C,k+1), R = r[k].x2;
        if(F < r[k].y1) sum += dfs(L,R,F,r[k].y1,k+1), F = r[k].y1;
        if(C > r[k].y2) sum += dfs(L,R,r[k].y2,C,k+1), C = r[k].y2;
        return sum;
    }
    
    int main() {
        scanf("%d%d%d",&a,&b,&n);
        for(int i = 1; i <= n; i++)
            scanf("%d%d%d%d%d",&r[i].x1,&r[i].y1,&r[i].x2,&r[i].y2,&r[i].col);
        ans[1] = a*b;
        for(int i = n; i >= 1; i--) {
            int s = dfs(r[i].x1,r[i].x2,r[i].y1,r[i].y2,i+1);
            ans[r[i].col] += s;
            ans[1] -= s;
        }
        for(int i = 1; i <= maxn; i++)
            if(ans[i])
                printf("%d %d
    ",i,ans[i]);
        return 0;
    }
    View Code
  • 相关阅读:
    DataAnnotations
    使用BizTalk实现RosettaNet B2B So Easy
    biztalk rosettanet 自定义 pip code
    Debatching(Splitting) XML Message in Orchestration using DefaultPipeline
    Modifying namespace in XML document programmatically
    IIS各个版本中你需要知道的那些事儿
    关于IHttpModule的相关知识总结
    开发设计的一些思想总结
    《ASP.NET SignalR系列》第五课 在MVC中使用SignalR
    《ASP.NET SignalR系列》第四课 SignalR自托管(不用IIS)
  • 原文地址:https://www.cnblogs.com/mogeko/p/11808393.html
Copyright © 2020-2023  润新知