我有这个背叛,这是一个背包问题的变种。
我有一个板(Knapstack类型,内部变量是int[][]
背包)和一个瓦片数组(大小为n
X m
,并非所有大小都相同。)如果我可以将所有瓷砖放在背包板内(不旋转它们),我需要编写一个返回true
的函数。例如:
如果图块尺寸为:
且电路板尺寸为4X4,可能的解决方案是:
这是我到目前为止的代码:
public boolean insertIntoKnapsack(Tile[] tiles) {
boolean ans = false;
ans=solution(this.knapsack,tiles,0,0,0);
return ans;
}
public boolean solution(int[][] knapsack, Tile[] tiles,int i,int j, int k) {
boolean ans=false; int a; int b=0;
if(j>=knapsack.length || k>=knapsack[0].length || i>=tiles.length)
return ans;
if(j<knapsack.length && k<knapsack[0].length && i==tiles.length) {
ans=isValid(knapsack,tiles);
return ans; }
for(a=0; knapsack.length-(j+a)>0 && a<tiles[i].getN(); a++) {
for(b=0; knapsack[0].length-(k+b)>0 && b<tiles[i].getM(); b++) {
if(knapsack[j+a][k+b]==0)
knapsack[j+a][k+b]=i+1;
}
}
return ans= solution(knapsack,tiles,i+1,j+a,k) || solution(knapsack,tiles,i+1,j,k+b) || solution(knapsack,tiles,i+1,j+a,k+b);
}
背包类定义为:
public class Knapsack {
// Holds the current state of the Knapsack
private int[][] knapsack;
public Knapsack(int n, int m) {
if(n<=0 || m<=0)
System.out.println("Bad Input");
else {
int knapsack[][] = new int[n][m];
}
}
函数isValid:
public boolean isValid(int[][] knapsack,Tile[] tiles) {
boolean ans=true;
for(int i=0;i<tiles.length; i++) {
int count=0;
for(int j=0; j<knapsack.length;j++) {
for(int k=0; k<knapsack[0].length; k++) {
if(knapsack[j][k]==i)
count=count+1;
}
}
if(count != tiles[i].getN() * tiles[i].getM())
ans=false;
}
return ans;
}
图块定义为:
public class Tile {
private int n;
private int m;
/*
* Construct a Tile of size nXm
*/
public Tile(int n, int m) {
if(n<=0 || m<=0)
System.out.println("Bad Input");
else {
this.n=n;
this.m=m;
}
}
/*
* Get the Tile's height
*/
public int getN(){
return n;
}
/*
* Get the Tile's width
*/
public int getM(){
return m;
}
}
不仅我不知道我的解决方案是否正确,每当我尝试测试它时,我得到NullPointerException
。我尝试在解决方法中更改for循环的条件,但无论我如何更改它,我都会遇到错误。有人可以告诉我,如果我使用解决方法以正确的方式前进,或者为什么我会继续获得NullPointerException
?