1) I have used "-1" to represent infinity. Hence I have an extra check to avoid the condition when "1 +(-1) = 0", because I want to treat "-1" as infinity and not number -1.
public class MakeChange{
int[][] c;
public int[] a;
int sum;
int numCoins;
public MakeChange(int targetSum, int[] coins){
sum = targetSum;
numCoins = coins.length;
a = coins;
c = new int[numCoins][sum + 1];
}
public int getMinCoins(){
c[0][0] = 0;
for(int i = 1; i <= sum; i++){
c[0][i] = -1; //This indicates infinite value, bcoz one cannot make sum of n using coin of value "0"
}
for(int i = 1; i < numCoins; i++){
for(int j = 1; j <= sum; j++){
System.out.println("Trying to make change for "+j+" using coin "+a[i]);
if(j < a[i]){ //sum to be made is less than coin value
System.out.println("Assign value of coin "+c[i-1][j]+" which is "+c[i-1][j]);
c[i][j] = c[i-1][j];
}else{ //Make sum j using coin i or without using coin i and select the one with min coins
int n = c[i][j-a[i]];
if(n < 0){ //This check is required as I am using -1 for infinity
c[i][j] = c[i-1][j];
}else{
System.out.println("Min of "+c[i-1][j]+" and "+(1+n));
int min = findMin(c[i-1][j],1+n);
c[i][j] = min;
}
}
}
}
System.out.println("The DP table is: ");
for (int i=0; i<c.length; i++) {
for (int j=0; j<c[i].length; j++) {
System.out.print(" " + c[i][j]);
}
System.out.println("");
}
return c[numCoins - 1][sum];
}
private int findMin(int i, int j){
if(i < 0 && j < 0) {
return -1; //return infinity
}else if(i < 0 && j >=0){
return j;
}else if(j < 0 && i >=0){
return i;
}else if(i < j){
return i;
}else{
return j;
}
}
public static void main(String args[]){
int[] a = {1,2,4,8};
MakeChange m = new MakeChange(8,a);
System.out.println("The min # of coins are "+m.getMinCoins());
}
}
No comments:
Post a Comment