Project: Cash Register not giving correct change back and a potential execution error

Hi there,

I have been working on the cash register for about 2 weeks now, at first I had no idea how to tackle the problem until I read the test cases and was able to work out that I had to return some sort of object and that I would need to access certain parts of the object to return the right output to pass the test cases. There are two areas I am stuck with:

  1. A potential error executing any code after the checks I made within the checkCashRegister function.

  2. Calculating change to return the correct change.

Last three test cases passed:
Test 4 - Passed
checkCashRegister(19.5, 20, [["PENNY", 0.01], ["NICKEL", 0], ["DIME", 0], ["QUARTER", 0], ["ONE", 0], ["FIVE", 0], ["TEN", 0], ["TWENTY", 0], ["ONE HUNDRED", 0]]) should return {status: "INSUFFICIENT_FUNDS", change: []}.

Test 5 - Passed
checkCashRegister(19.5, 20, [["PENNY", 0.01], ["NICKEL", 0], ["DIME", 0], ["QUARTER", 0], ["ONE", 1], ["FIVE", 0], ["TEN", 0], ["TWENTY", 0], ["ONE HUNDRED", 0]]) should return {status: "INSUFFICIENT_FUNDS", change: []}.

Test 6 - Passed
checkCashRegister(19.5, 20, [["PENNY", 0.5], ["NICKEL", 0], ["DIME", 0], ["QUARTER", 0], ["ONE", 0], ["FIVE", 0], ["TEN", 0], ["TWENTY", 0], ["ONE HUNDRED", 0]]) should return {status: "CLOSED", change: [["PENNY", 0.5], ["NICKEL", 0], ["DIME", 0], ["QUARTER", 0], ["ONE", 0], ["FIVE", 0], ["TEN", 0], ["TWENTY", 0], ["ONE HUNDRED", 0]]}

This just leaves the two test cases for when the status of the cash register had a status of “OPEN”.

However, within the checkCashRegister function, after the checks for “INSUFFICIENT_FUNDS” and “CLOSED” test cases have been executed. It looks like any other code after the last check doesn’t seem to execute including anything logged to the console. This is where I am trying to call a function “calculateChange” to return any change to the customer. I commented out the check for “INSUFFICIENT_FUNDS” to test if the code after these checks would work and this allows the code after the checks to run. I would like some clarification on this as I believe I might be doing something wrong with the first check for the test cases for “INSUFFICIENT_FUNDS”.

Secondly, within my function “calculateChange” I am mapping through the “changeInDrawer” and calculating how many coins make up the total for each currency unit. So long as there are sufficient coins within the drawer I am able to take the current coin value and multiply it by the number of coins used. However, based on a check where the
changeRemaining >= coinValue && coinAmount > 0 which would first isolate the available coins to use to ensure I return the correct change, secondly the condition will run so long as there are coins available in the drawer. It seems the check only runs once for each currency unit and moves on to the next currency unit within the array.

Should I be including an extra condition within this check to ensure its keeps adding the same value until it is more than the change remaining?

calculateChange method:
var calculateChange = function(changeRemaining, changeInDrawer) {

  const denomination = [100, 20, 10, 5, 1, 0.25, 0.1, 0.05, 0.01];
  var change = [];

  changeInDrawer.map((slot, i) => {
    const coinName = slot[0];
    const coinTotal = slot[1];
    const coinValue = denomination[i];
    let coinAmount = (coinTotal / coinValue.toFixed(2));
    let coinsToReturn = 0;
    // checks against each currency unit.
    if (changeRemaining >= coinValue && coinAmount > 0) {
      changeRemaining -= coinValue;
      changeRemaining = changeRemaining.toFixed(2);
      coinAmount--;
      coinsToReturn++;
    }
    if (coinsToReturn > 0) {
    change.push([coinName, coinsToReturn * coinValue])
    }
    
  })
  return change;
}
checkCashRegister method:
var checkCashRegister = function(price, cash, cid) {

  const registerStatus = {
    insufficient_funds: {
      status: "INSUFFICIENT_FUNDS",
      change: []
    },
    closed: {
      status: "CLOSED",
      change: []
    },
    open: {
      status: "OPEN",
      change: []
    }
  }

  var changeDue = cash - price;
  changeDue = changeDue.toFixed(2);
  var changeAvailable = cid.slice();
  var totalChange = 0;

  changeAvailable.map(item => {
     return totalChange += item[1];
  });
  
  totalChange = totalChange.toFixed(2);
  
  // calculateChange FUNCION DOESN'T WORK WHEN THE BELOW CONDITION RUNS.

  // if (totalChange < changeDue || totalChange != changeDue) {
  //   return registerStatus.insufficient_funds;
  // } 

  if (totalChange == changeDue) {
     registerStatus.closed.change = [...cid];
     return registerStatus.closed;
  } 

  registerStatus.open.change = calculateChange(changeDue, changeAvailable.reverse());
  return registerStatus.open; 
}

Full Test cases:
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]]) should return an object.

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]]) should return {status: "OPEN", change: [["QUARTER", 0.5]]}.

checkCashRegister(3.26, 100, [["PENNY", 1.01], ["NICKEL", 2.05], ["DIME", 3.1], ["QUARTER", 4.25], ["ONE", 90], ["FIVE", 55], ["TEN", 20], ["TWENTY", 60], ["ONE HUNDRED", 100]]) should return {status: "OPEN", change: [["TWENTY", 60], ["TEN", 20], ["FIVE", 15], ["ONE", 1], ["QUARTER", 0.5], ["DIME", 0.2], ["PENNY", 0.04]]}.

checkCashRegister(19.5, 20, [["PENNY", 0.01], ["NICKEL", 0], ["DIME", 0], ["QUARTER", 0], ["ONE", 0], ["FIVE", 0], ["TEN", 0], ["TWENTY", 0], ["ONE HUNDRED", 0]]) should return {status: "INSUFFICIENT_FUNDS", change: []}.

checkCashRegister(19.5, 20, [["PENNY", 0.01], ["NICKEL", 0], ["DIME", 0], ["QUARTER", 0], ["ONE", 1], ["FIVE", 0], ["TEN", 0], ["TWENTY", 0], ["ONE HUNDRED", 0]]) should return {status: "INSUFFICIENT_FUNDS", change: []}.

checkCashRegister(19.5, 20, [["PENNY", 0.5], ["NICKEL", 0], ["DIME", 0], ["QUARTER", 0], ["ONE", 0], ["FIVE", 0], ["TEN", 0], ["TWENTY", 0], ["ONE HUNDRED", 0]]) should return {status: "CLOSED", change: [["PENNY", 0.5], ["NICKEL", 0], ["DIME", 0], ["QUARTER", 0], ["ONE", 0], ["FIVE", 0], ["TEN", 0], ["TWENTY", 0], ["ONE HUNDRED", 0]]}.

Thank you for your time and attention.

Tom

I think you cannot use this logic

 if (totalChange < changeDue || totalChange != changeDue) {
    return registerStatus.insufficient_funds;
 } 

for example, the first case the totalChange is not equal to changeDue, basically every case wherethe totalChange is different from the changeDue will stop the program and return insufficient fund. When you use return it will exit the function and will never run the rest of the code