zoukankan      html  css  js  c++  java
  • [USACO 6.2.3] Shaping Regions

    题目大意

      N个不同颜色矩形放在同一方框内,每个矩形都至少有一部分被看见,求每个矩形被看见的面积.

    题解

      这道题和usaco以前做过的某道题我感觉很类似.

      使用漂浮法,或者说是矩形分割法.

      想象一下,每个矩形有一个层次标记.低层次的会被高层次的覆盖.我们想象一下低层次的矩形向上漂浮,然后撞到了一个矩形.然后这个漂浮ing的矩形就会分割成若干个矩形.然后这若干个矩形继续向上漂浮.直到漂浮到水面上或者说没有比它更高层次的矩形时停下来统计面积即可.

      利用上面所述的漂浮法的思想可以得到O(N2)的算法.

    代码

    /*
    TASK:rect1
    LANG:C++
    */
    
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    
    using namespace std;
    
    struct Matrix
    {
        int x1, y1, x2, y2, cr;
    }mat[1005];
    
    int cnt[2505], n;
    
    int floatup(int x1, int y1, int x2, int y2, int k)
    {
        if (x2 < x1 || y2 < y1) return 0;
        if (k == n + 1) return (x2 - x1 + 1) * (y2 - y1 + 1);
        if (x1 > mat[k].x2 || x2 < mat[k].x1 || y1 > mat[k].y2 || y2 < mat[k].y1)
            return floatup(x1, y1, x2, y2, k + 1);
        return floatup(x1, y1, mat[k].x1 - 1, y2, k + 1)
                + floatup(max(x1, mat[k].x1), y1, min(x2, mat[k].x2), mat[k].y1 - 1, k + 1)
                + floatup(max(x1, mat[k].x1), mat[k].y2 + 1, min(x2, mat[k].x2), y2, k + 1)
                + floatup(mat[k].x2 + 1, y1, x2, y2, k + 1);
    }
    
    int main()
    {
        freopen("rect1.in", "r", stdin);
        freopen("rect1.out", "w", stdout);
        mat[0].x1 = mat[0].y1 = 0;
        mat[0].cr = 1;
        scanf("%d%d%d", &mat[0].x2, &mat[0].y2, &n);
        mat[0].x2--;
        mat[0].y2--;
        for (int i = 1; i <= n; ++i)
        {
            scanf("%d%d%d%d%d", &mat[i].x1, &mat[i].y1, &mat[i].x2, &mat[i].y2, &mat[i].cr);
            mat[i].x1 = max(mat[i].x1, mat[0].x1);
            mat[i].y1 = max(mat[i].y1, mat[0].y1);
            mat[i].x2 = min(mat[i].x2-1, mat[0].x2);
            mat[i].y2 = min(mat[i].y2-1, mat[0].y2);
        }
        memset(cnt, 0, sizeof(cnt));
        cnt[mat[n].cr] = (mat[n].x2 - mat[n].x1 + 1) * (mat[n].y2 - mat[n].y1 + 1);
        for (int i = n-1; i >= 0; --i)
            cnt[mat[i].cr] += floatup(mat[i].x1, mat[i].y1, mat[i].x2, mat[i].y2, i + 1);
        for (int i = 1; i <= 2500; ++i)
            if (cnt[i]) printf("%d %d
    ", i, cnt[i]);
        return 0;
    }
  • 相关阅读:
    octotree神器 For Github and GitLab 火狐插件
    实用篇如何使用github(本地、远程)满足基本需求
    PPA(Personal Package Archives)简介、兴起、使用
    Sourse Insight使用过程中的常使用功能简介
    Sourse Insight使用教程及常见的问题解决办法
    github 遇到Permanently added the RSA host key for IP address '192.30.252.128' to the list of known hosts问题解决
    二叉查找树的C语言实现(一)
    初识内核链表
    container_of 和 offsetof 宏详解
    用双向链表实现一个栈
  • 原文地址:https://www.cnblogs.com/albert7xie/p/5732969.html
Copyright © 2011-2022 走看看