Find out what's wrong with the following program?

var cnt = 0;
function change(target, coins, usable) {
    coin = coins.shift();
    if(coins.length==0) {
        if(target/coin<=usable) {
            cnt += 1;
        }
    }
    else{
        for(let i=0; i<=target/coin; iPP) {
            change(target-coin*i, coins, usable-i);
        }
    }
}
change(1000, [500, 100, 50, 10], 15);
console.log(cnt);

algorithm topic link: https://max.book118.com/html/..

topic: at present, most people swipe their credit cards when they take the bus or subway. Today, however, more people are still paying in cash than expected. This topic is based on the change machine placed on the bus.

this machine can exchange banknotes for a combination of 10 yen, 50 yen, 100 yen and 500 yen coins, and there are enough coins for each type (because the minimum limit accepted by bus is 10 yen, so 1 yen and 5 yen coins are not provided).

When exchanging, the machine is allowed to exchange coins that can not be used in this payment. In addition, because it is inconvenient to exchange a large amount of change when taking the bus, the machine is only allowed to exchange up to 15 coins. For example, when you exchange a 1000 yen note, you cannot exchange it for a combination of 100 10 yen coins.

how many combinations will occur when you ask for 1000 yen notes? Note that the order in which the coins are redeemed is not taken into account.

Mar.15,2021

var cnt = 0;
function change(target, coins, usable) {
    let coin = coins.shift();//coin,for,target/coin<=usable.
    if(coins.length==0) {
        if(target/coin<=usable) {
            cnt += 1;
        }
    }
    else{
        for(let i=0; i<=target/coin; iPP) {
            change(target-coin*i, coins.slice(), usable-i);//coins,shift.
        }
    }
}
change(1000, [500, 100, 50, 10], 15);
console.log(cnt);

coins.shift () usable doesn't know how to define some of your content?


is unexpectedly an algorithm problem.
I can't open this link of yours, but I have no choice but to face .gif

my answer


var cnt = 0, pagerCoin = 1000;
//
//  a500 b100 c50 d10
//  a+b+c+d <=15
// 500a+100b+50c+10d = 1000

// 
function getOneCoinsMaxNumber(pagerCoin,coin){
  return Math.floor(pagerCoin/coin)
}

let abcd = [];
//  abcd
for(let at,ai = (at=getOneCoinsMaxNumber(pagerCoin, 500)) > 15 ? 15 : at; ai >= 0; ai--)
  for(let bt,bi = (bt=getOneCoinsMaxNumber(pagerCoin,100)) > 15 ? 15 : bt; bi >= 0; bi--)
    for(let ct,ci = (ct=getOneCoinsMaxNumber(pagerCoin,50)) > 15 ? 15 : ct; ci >= 0; ci--)
      for(let dt,di = (dt=getOneCoinsMaxNumber(pagerCoin,10)) > 15 ? 15 : dt; di >= 0; di--)
        console.log(ai,bi,ci,di,abcd.push([ai,bi,ci,di]))
// abcd
console.log(abcd)
let coins = [500,100,50,10]
//  
let rule1 = arr => arr.reduce((init,item) => init+=item,0)
let rule2 = arr => arr[0]*coins[0]+arr[1]*coins[1]+arr[2]*coins[2]+arr[3]*coins[3]
// 
let d =abcd.filter(item => rule1(item) <= 15 && rule2(item) == 1000)
console.log(d);

the results are as follows: this method is relatively rough, first posted to give you a reference, your way you do not have to explain and comment, so it is difficult to understand, so did not read it.


since it is an algorithm problem, we should first consider the algorithm
. In fact, after the problem is transformed, we should find four different numbers in the array A, extract each number (allow multiple extraction) and extract a total of digits N (N < = 15), so that the sum is equal to X, and ask how much it is possible (at least 0, that is, can not match the extraction)
of course, because X and An in this question have been determined, so the search size can be reduced.
previously given a method, I want to use another method to solve (bit operation)
according to some of the previous conditions, it may actually be mapped to a 2bit (maximum value is 3) + 4bit (maximum value is 15) + 4bit (maximum value is 15) + 4bit (maximum value is 15) is numerically
where 2bit corresponds to the number of 500s, because the number that happens to be equal to 2 is unique. Therefore, it can be reduced to the number of 1bit+4bit+4bit+4bit (a total of 13bit)
and the sum of each segment of data is less than or equal to 15, and the second segment is also less than or equal to 10, so you can get the final result by traversing the qualified number. The following is the implementation (this problem is not the optimal solution for this, but if the amount of A data is expanded, N and X are enlarged, then it may be a better solution, because it is simply traversed, it is an O (N) complexity algorithm), and the implementation logic of this algorithm is relatively simple, and the sentence is also relatively simple.

var A=[500,100,50,10];//
var RT=[[2,0,0,0]];//
var s=0x1AFF; //
for(;s>0;s--){
    //
    a0=s>>12;
    a1=(s>>8)&0xf;
    a2=(s>>4)&0xf;
    a3=s&0xf;
    if(a1>10 || a0+a1+a2+a3>15) continue; // 
    if(a0*A[0]+a1*A[1]+a2*A[2]+a3*A[3] ===1000) RT.push([a0,a1,a2,a3]);
}
console.log(RT);
var cnt=RT.length;
console.log(cnt);//
Menu