Section 3.1 Shaping Regions Again

这次用了矩形分割的方法实现了下,参考了的代码,用了上浮+矩形分割的思想,个人觉得递归的写法更形象,且方便,于是,看了04年薛矛大牛论文后,实现了这个方法,觉得很赞,先从X方向上割掉,再割掉Y方向上。不过最糟糕复杂度是O(N^3),这个还是很可怕的,但一般是达不到的,这里的11个数据,都在0.1s以下,这种方法是解决一类统计类问题的利器~

下面是薛大牛论文中的伪码:

Cut

下面是用矩形分割实现该题的代码:

/*
ID: litstrong
PROG: rect1
LANG: C++
*/
#include <iostream>
#include <string>
#include <vector>
#include <set>
#include <math.h>
#include <queue>
#include <algorithm>
#include <string.h>
#include <stdio.h>
using namespace std;
 
const int MAXN = 10005;
const int MAXC = 2505;
 
int c_ans[MAXC];
int A, B, N;
 
class CRECT
{
public:
    int nx, mx, ny, my, c;
public:
    CRECT() {}
    CRECT(int _nx, int _mx, int _ny, int _my, int _c) :
    nx(_nx), mx(_mx), ny(_ny), my(_my), c(_c) {}
}rect[MAXN];
 
void CutFloat(int level, int x1, int y1, int x2, int y2, int c)
{
    if(level > N)
    {
        c_ans[c] += (x2 - x1) * (y2 - y1);
        return;
    }
    int x3 = rect[level].nx, y3 = rect[level].ny;
    int x4 = rect[level].mx, y4 = rect[level].my;
    if(x3 >= x2 || x4 <= x1 || y3 >= y2 || y4 <= y1)
        CutFloat(level + 1, x1, y1, x2, y2, c);
    else
    {
        int k1, k2, k3, k4;
        //x
        k1 = max(x1, x3); k2 = min(x2, x4);
        if(x1 < k1)  CutFloat(level + 1, x1, y1, k1, y2, c);
        if(k2 < x2)  CutFloat(level + 1, k2, y1, x2, y2, c);
        //y
        k3 = max(y1, y3); k4 = min(y2, y4);
        if(y1 < k3)  CutFloat(level + 1, k1, y1, k2, k3, c);
        if(k4 < y2)  CutFloat(level + 1, k1, k4, k2, y2, c);
    }
}
 
int main()
{
    freopen("rect1.in", "r", stdin);
    freopen("rect1.out", "w", stdout);
 
    scanf("%d%d%d", &A, &B, &N);
    rect[0] = CRECT(0, A, 0, B, 1);
 
    for(int i = 1; i <= N; i++)
    {
        int nx, mx, ny, my, c;
        scanf("%d%d%d%d%d", &nx, &ny, &mx, &my, &c);
        rect[i] = CRECT(min(nx, mx), max(nx, mx), min(ny, my), max(ny, my), c);
    }
 
    memset(c_ans, 0, sizeof(c_ans));
 
    //上浮
    for(int i = N; i >= 0; i--)
    {
        CutFloat(i + 1, rect[i].nx, rect[i].ny, rect[i].mx, rect[i].my, rect[i].c);
    }
 
    for(int i = 0; i < MAXC; i++)
        if(c_ans[i])  printf("%d %d\n", i, c_ans[i]);
}

你可能感兴趣的:(ping)