二维递归背包

时间:2015-01-05 17:35:11

标签: java arrays recursion 2d knapsack-problem

假设我们有一个瓦片阵列,每个瓦片的大小为n,而一个2d阵列用作棋盘。

我想编写一个递归函数,如果可以适合电路板中的所有瓷砖,则返回true,否则返回false(无论电路板是否填充,只需要使用所有瓷砖)。

我尝试了几种不成功的方式。

解决方案不一定是最佳的。

3 个答案:

答案 0 :(得分:0)

我认为贪婪的算法策略可能适合您的要求。我发现了一个贪婪的aglorithm策略,在这里递归实现:www.cs.siu.edu/~mcoleman/classwork/cs330bonus/Knapsack.java

我自己没有仔细查看解决方案,以确定它是否适合您。但是,我确信您可以选择的一个潜在选项是贪婪的算法策略。

答案 1 :(得分:0)

尝试以下方法。您需要实现各种电路板实用程序功能,例如返回可能的电路板位置列表。我假设你没问题 - 它主要是你感兴趣的递归搜索算法。

boolean canFit(List<Tile> tiles, Board board) {
    if (tiles.isEmpty()) {
        return true;
    } else {
        for (Tile tile: tiles) {
            tiles.remove(tile);
            for (Position position: board.possiblePositionsFor(tile)) {
                board.addTile(tile, position);
                if (canFit(tiles, board)) 
                    return true;
                board.removeTile(tile);
            }
            tiles.add(tile);
        }
        return false;
    }
}

如果您可以创建新的图块集并删除图块并使用单个方法添加图块的新图块,则代码将更整洁。然后你可以摆脱所有的陈述来改变瓷砖组和电路板,只需用以下内容替换它们:

boolean canFit(TileSet tiles, Board board) {
    return tiles.isEmpty() || 
        tiles.stream()
            .flatmap(tile -> board.streamPossiblePositionsFor(tile)
                .filter(pos -> canFit(tiles.remove(tile), board.add(tile, pos))
            .findAny().isPresent();
}

使用哪一套 - 第二种效率较低,因为它创造了许多新的瓷砖组和板,但它也有点整洁。

答案 2 :(得分:-1)

您可以使用嵌套for循环遍历2d数组中的每个空格来尝试每个空格。

for(int x = 0; x < arraysizex; x++)
{
    for(int y = 0; y < arraysizey; y++)
        if(array[x][y] != filled)
        {
            //do something
        }
}