Cash Register - Comparison problem with the while loop?

Tell us what’s happening:
Hi Fellow Code Campers -

I’m trying to figure out what is going on with this loop:

console.log("change is greater than Zero.");
while (nPrice > 0) {
    for (let i = moneyKey.length - 1; i > 0; --i) {
        console.log("price left in loop: " + nPrice);
        console.log("money key index: " + moneyKey[i]);

        if (nPrice >= moneyKey[i]) {    
            nPrice -= moneyKey[i];
            //                  updateCID(moneyKey[i], i);
            nPrice = nPrice.toFixed(2);
            break;
        }
    }

    console.log("End for Price: " + nPrice);
}

It’s returning output that doesn’t make sense. For some reason the (nPrice >= moneyKey[i]) works until it makes the first update to nPrice, then after that it’s like the comparison stops working??? I’m very confused. This is the console.log output:

change is greater than Zero.
price left in loop: 19.5
money key index: 100 <- This works, 19.5 is not greater than 100
price left in loop: 19.5
money key index: 20 <- This works, 19.5 is not greater than 20
price left in loop: 19.5
money key index: 10 <- This works, 10 is less than 19.5 so it subtracts 10 from nPrice
End for Price: 9.50
price left in loop: 9.50
money key index: 100 <- This doesn’t work, 9.50 is less than 100, but the loops stops and it subtracts 100 from 9.50. Is there something special about decimals comparisons I should know???
End for Price: -90.50
ending CID: PENNY,1.01,NICKEL,2.05,DIME,3.1,QUARTER,4.25,ONE,90,FIVE,55,TEN,20,TWENTY,60,ONE HUNDRED,100

Not sure what’s going on, this type of loop worked for my roman numeral code. Any suggestions? Thanks!

Your code so far


function checkCashRegister(price, cash, cid) {
    let drawerOpen = {
        status: "OPEN",
        change: []
    };

    let drawerClosed = {
        status: "CLOSED",
        change: []
    };

    let drawerInsuf = {
        status: "INSUFFICIENT_FUNDS",
        change: []
    };

    let moneyKey = [
        [.01], [.05], [.10], [.25], [1],
        [5], [10], [20], [100]
    ];

    console.log("Initial CID: ");
    console.log(cid);

    let change = cash - price;   // calculate change due back
    let nPrice = price;

    console.log("change due back: " + change);
    console.log("cash: " + cash);
    console.log("price: " + price);

    function updateCID(amount, index) {   // updates the amount of cash in the drawer

        console.log("init amount: " + amount);
        console.log("index: " + index);

        if (cid[0][index] < amount) { // returns insufficient funds if ran out of money in drawer
            console.log("Drawer Insuf CID: " + cid);
            return drawerInsuf;
        }
        else
            cid[0][index] -= amount;   // subtracts amount from drawer

        console.log("updated CID Index " + cid[0][index]);
    }

    if (change <= 0)  // if no change is due back, update cash in drawer and return drawer closed.
    {
        console.log("Change is Zero.");

        while (nPrice > 0) {
            for (let i = moneyKey.length; i > 0; --i) {
                if (nPrice >= moneyKey[i]) {
                    nPrice -= moneyKey[i];
                    //                    updateCID(moneyKey[i], i);
                }
            }
        }

        drawerClosed.change = cid;

        console.log("Drawer Closed: " + drawerClosed.change);
        return drawerClosed;
    }

    console.log("change is greater than Zero.");
    while (nPrice > 0) {
        for (let i = moneyKey.length - 1; i > 0; --i) {
            console.log("price left in loop: " + nPrice);
            console.log("money key index: " + moneyKey[i]);

            if (nPrice >= moneyKey[i]) {    
                nPrice -= moneyKey[i];
                //                  updateCID(moneyKey[i], i);
                nPrice = nPrice.toFixed(2);
                break;
            }
        }

        console.log("End for Price: " + nPrice);
    }





    console.log("ending CID: " + cid);

    return drawerOpen;   // Here is your change, ma'am.
}

// Example cash-in-drawer array:
// [["PENNY", 1.01],
// ["NICKEL", 2.05],
// ["DIME", 3.1],
// ["QUARTER", 4.25],
// ["ONE", 90],
// ["FIVE", 55],
// ["TEN", 20],
// ["TWENTY", 60],
// ["ONE HUNDRED", 100]]

checkCashRegister(19.5, 20, [["PENNY", 1.01], ["NICKEL", 2.05], ["DIME", 3.1], ["QUARTER", 4.25], ["ONE", 90], ["FIVE", 55], ["TEN", 20], ["TWENTY", 60], ["ONE HUNDRED", 100]]);

Your browser information:

User Agent is: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/67.0.3396.99 Safari/537.36.

Link to the challenge:
https://learn.freecodecamp.org/javascript-algorithms-and-data-structures/javascript-algorithms-and-data-structures-projects/cash-register/

It works first time when your array loops over [0.25] but it’s only going to subtract this amount once so 0.5 - 0.25 = 0.25. Then it goes down the loop and will stop at 0.5 and so forth…

A few things I see…

moneyKey[i] is an array, not a number
if (nPrice >= moneyKey[i]) { so this comparison is not always working as expected.
if (nPrice >= moneyKey[i][0]) { would work but not sure why moneyKey is made of subarrays

Why are you looping through calculating the price? You should be making change to give back to customer so a loop through making change of .50 is what you would want for first test of challenge.

The order of your logic is off. You are looping through each denomination 100,20, 10…
If you owe back $55 you would want to pay out 20, 20, 10, 5. Your loop would pay out 20 and move on to 10.

Ok, well I finally figured this one out, after learning a lot more about loops and objects.

I have to say this challenge was one of the most difficult and time consuming so far, but I am glad I finished. The instructions should be a bit clearer, that you don’t have to add the new money you’re given to the CID.

I assumed you would, that would make more sense. If someone gives you a $20, and the price is $19.50, then you give them .50 cents in change, but the $20 also goes into the drawer. Meaning you would add $20 to the drawer.

The test solutions don’t account for this.