固定大小的正方形包装在有障碍物的网格上

时间:2018-11-26 11:29:58

标签: algorithm matrix language-agnostic dynamic-programming

我正在寻找一种算法,该算法将在具有障碍物的网格中找到给定大小的所有非重叠正方形。所有正方形必须具有相同的大小,并将其作为输入之一。

示例网格,其中黑色单元格代表空白区域,红色单元格代表障碍物。接下来是在网格中找到多个5x5黄色正方形的示例解决方案:

enter image description here enter image description here

到目前为止,我所掌握的是一种使用动态编程找到最大平方的算法,但我不知道它是否对上述问题有用。也许可以修改它以找到多个正方形。

var width = 10, height = 10;
var grid = new Array(width * height);
var sizes = new Array(width * height);

function findBiggestSquare() {
    var bestSize = -1, bestLocation = -1;

    for (var i = grid.length - 1; i >= 0; i--) {
        var size = 0;

        if (grid[i] === 0) {
            size = 1 + Math.min(sizes[i+1], sizes[i+width], sizes[i+1+width]);

            if (size > bestSize) {
                bestSize = size;
                bestLocation = i;
            }
        }

        sizes[i] = size;
    }

    if (bestLocation !== -1)
        return {'size': bestSize, 'location': bestLocation};
    else
        return null;
}

1 个答案:

答案 0 :(得分:1)

通过检查网格的每个NxN部分中的障碍物,可以轻松找到此类正方形的所有潜在中心。可以进行一些直接的优化。这是您的示例,其中的潜在中心为橙色:

highlighted potential centers

尽管拾取中央单元格更容易可视化,但您可能需要使用角落。这样,您不必担心N的奇偶性,其余的可能更简单。

一旦有了这些突出显示的单元格,请为每个单元格分配一个数字,该数字等于如果在其中放置一个正方形将不可用的其他突出显示的单元格数。例如,如果您具有潜在的左上角列表,则分配给其中一个的数字就是以2*N-1正方形为中心的潜在的左上角数量。

然后,选择编号最小的单元格放一个正方形,并相应地更新网格。重复直到您的列表为空。