矩形网格 mxn,应填充 m*n/2 2x1 多米诺骨牌,可以水平或垂直放置。存在多少种可能的解子?
我试图用递归来解决这个问题(是的,我知道这可以很容易地用斐波那契计算)。
private static void place(int row, int col, int[][] rectangle) {
if (canBePlacedHorizontally(row, col, rectangle)) {
rectangle = deepCopy(rectangle);
placeHorizontally(row, col, rectangle);
decideNextMove(row, col, rectangle);
}
if (canBePlacedVertically(row, col, rectangle)) {
rectangle = deepCopy(rectangle);
placeVertically(row, col, rectangle);
decideNextMove(row, col, rectangle);
}
}
private static void decideNextMove(int row, int col, int[][] rectangle) {
if (rectangleIsFilled(rectangle)) {
count = count.add(BigInteger.ONE);
}
else if(row == rectangle.length -1) {
place(0, col+1, rectangle);
}
else{
place(row+1, col, rectangle);
}
}
private static BigInteger calculate(int m, int n) {
int[][] rectangle = new int[m][n];
place(0, 0, rectangle);
return count;
}
该deepCopy()方法只是通过迭代数组并使用 来重新创建二维数组Arrays.copyOf()。
如果我calculate(2,2)通过水平添加多米尼奥并将矩形更改为[[1,1][0,0]]. 然后它转到同一列中的下一行(row=1,col=0)并再次放置一个水平多米诺骨牌,因此矩形看起来像[[1,1][1,1]]。它检测到矩形已填充并将 1 添加到count. 然后它继续检查是否可以将垂直多米诺骨牌放置在 (row=1, col=0) 和已经填充的数组,这显然不起作用。然后它回退并检查是否可以将垂直多米诺骨牌放置在 (row=0, col=0) 与前一个数组[[1,1][0,0]],这也不起作用。然后它完成。
让我感到困惑的是,canBePlacedVerticallyplace 方法中的if 块使用“新”参数调用。在示例中,我希望它首先使用[[1,1][0,0]]数组然后使用[[0,0][0,0]]数组调用该方法。谁能看到我的问题在哪里?我猜它与数组被复制的地方有关,但我不确定......
感谢您的帮助
相关分类