JavaScript Algorithms and Data Structures ProjectsCash Register

My code returns the right answers but FCC doensn’t accept it. Can someone explain why?

const cidToValue = (cid)=>

{let newArr = [ ];

for(let i = 0 ; i<cid.length;i++){

newArr[i]= cid[i].toString();

newArr[i]= newArr[i].match(/[0-9].*/g);

newArr[i]= newArr[i].join("");

newArr[i] = parseFloat(newArr[i], 10);

}

const reducer = (a,b) => a + b;

let b = newArr.reduce(reducer);

b=b.toFixed(2);

return b;

}

const valueToCid = (change,cid) => {

let newArr = [ ];

for(let i = 0 ; i<cid.length;i++){

newArr[i]= cid[i].toString();

newArr[i]= newArr[i].match(/[0-9].*/g);

newArr[i]= newArr[i].join("");

newArr[i] = parseFloat(newArr[i], 10);

}

let values = [0.01,0.05,0.1,0.25,1,5,10,20,100];

let count = [0,0,0,0,0,0,0,0,0];

let names =[["PENNY"], ["NICKEL"], ["DIME"], ["QUARTER"], ["ONE"], ["FIVE"], ["TEN"], ["TWENTY"], ["ONE HUNDRED"]];

let save = change;

let y = values.length-1;

if (change > 0){

while (change>0){

if(change >= values[y] && newArr[y]> (count[y] *values[y]))

{count[y]++;

change = change-values[y];

}

else y--;}

}

if (change > 0){

count[0]++;

}

let final = [];

for(let i = 9; i >=0;i--){

if(values[i]*count[i] > 0){

final.push([names[i], values[i]*count[i]]);

}

}

if(cidToValue(final) != save){

return false};

return final;

}

function checkCashRegister(price, cash, cid) {

let change = cash - price;

// Here is your change, ma'am.

let output = {

status : null,

change : []

}

if(change > cidToValue(cid)) {output.status = "INSUFFICIENT_FUNDS"; output.change = []; return output}

else if (!valueToCid(change,cid)) {output.status = "INSUFFICIENT_FUNDS"; output.change = []; return output}

else if ( change == cidToValue(cid)){output.status = "CLOSED"; output.change = cid; return output}

else {output.status = "OPEN"; output.change = valueToCid(change,cid);console.log((output.change)); return output;}

}

// 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]])

So… a suggestion. In each branch of your if (within the checkCashRegister), you set the values on output and immediately return that. Make a change. Remove the return from each branch of the if statement, simply use the if to set the values, then move the return OUTSIDE that. Doing so, you can debug.

I did what I mentioned to your code, and I added a console.log just before I return. So again, remove all the return statements from the if branches, and put these two lines in at the very end of the checkCashRegister function:

  console.log(`For (price=${price}, cash=${cash}, cid=${JSON.stringify(cid)}, \n what we're returning: ${JSON.stringify(output)}`)

  return output;

Here’s one example of what the console.log I’ve written is showing:

For (price=19.5, cash=20, cid=[["PENNY",1.01],["NICKEL",2.05],["DIME",3.1],["QUARTER",4.25],["ONE",90],["FIVE",55],["TEN",20],["TWENTY",60],["ONE HUNDRED",100]], 
 what we're returning: {"status":"OPEN","change":[[["QUARTER"],0.5]]}

… do you see a problem with that return value? Specifically, within the returned change?

Thanks for trying to help, man!
I’m a begginner at JavaScript so i don’t know what JSON means yet.
but i think i tried what you said with this and i still have the same problem… And with problem i mean that even tough my code returns the same arrays as the FCC answers. It doensn’t accept it. :confused:

if(change > cidToValue(cid)) {output.status = "INSUFFICIENT_FUNDS"; output.change = [];}

else if (!valueToCid(change,cid)) {output.status = "INSUFFICIENT_FUNDS"; output.change = [];}

else if ( change == cidToValue(cid)){output.status = "CLOSED"; output.change = cid; }
 
else  {output.status = "OPEN"; output.change =[ valueToCid(change,cid)];console.log((output.change)); }


return output;
} 

For the 2nd test case, your function is returning the following

{
  status: "OPEN",
  change:[[["QUARTER"],0.5]]
}

instead of the correct result of

{
  status: "OPEN",
  change:[["QUARTER",0.5]]
}

You are returning a three-dimensional array instead of a two-dimensional array.

FYI - It would be in your best interest and help others if you would properly indent your code and remove the unnecessary extra blank lines (see example below). It makes it much easier to read while taking still taking up less space.

const cidToValue = (cid) => {
  let newArr = [];
  for (let i = 0; i < cid.length; i++) {
    newArr[i] = cid[i].toString();
    newArr[i] = newArr[i].match(/[0-9].*/g);
    newArr[i] = newArr[i].join("");
    newArr[i] = parseFloat(newArr[i], 10);
  }

  const reducer = (a, b) => a + b;
  let b = newArr.reduce(reducer);
  b = b.toFixed(2);
  return b;
}

const valueToCid = (change, cid) => {
  let newArr = [];
  for (let i = 0; i < cid.length; i++) {
    newArr[i] = cid[i].toString();
    newArr[i] = newArr[i].match(/[0-9].*/g);
    newArr[i] = newArr[i].join("");
    newArr[i] = parseFloat(newArr[i], 10);
  }

  let values = [0.01, 0.05, 0.1, 0.25, 1, 5, 10, 20, 100];
  let count = [0, 0, 0, 0, 0, 0, 0, 0, 0];

  let names = [["PENNY"], ["NICKEL"], ["DIME"], ["QUARTER"], ["ONE"], ["FIVE"], ["TEN"], ["TWENTY"], ["ONE HUNDRED"]];

  let save = change;
  let y = values.length - 1;

  if (change > 0) {
    while (change > 0) {
      if (change >= values[y] && newArr[y] > (count[y] * values[y])) {
        count[y]++;
        change = change - values[y];
      }
      else y--;
    }
  }

  if (change > 0) {
    count[0]++;
  }

  let final = [];

  for (let i = 9; i >= 0; i--) {
    if (values[i] * count[i] > 0) {
      final.push([names[i], values[i] * count[i]]);
    }
  }

  if (cidToValue(final) != save) {
    return false
  };

  return final;
}

function checkCashRegister(price, cash, cid) {

  let change = cash - price;

  // Here is your change, ma'am.

  let output = {
    status: null,
    change: []
  }

  if (change > cidToValue(cid)) {
    output.status = "INSUFFICIENT_FUNDS";
    output.change = []; return output
  } else if (!valueToCid(change, cid)) {
    output.status = "INSUFFICIENT_FUNDS";
    output.change = []; return output
  } else if (change == cidToValue(cid)) {
    output.status = "CLOSED";
    output.change = cid; return output
  } else {
    output.status = "OPEN";
    output.change = valueToCid(change, cid);
    console.log((output.change)); return output;
  }
}
1 Like

the values you store in your names array, within the valueToCid(), are what seems to be causing most of your problem. Why are your names an array, with each item being an array, with each of THEIR items being a string? All you want names to be is… an array of strings.

 // an array of strings
const myStringArray = ["first","second","third"];

// this is an array, containing three sub-arrays, each containing a single member, a string
const myNestedStringArray = [ ["first"], ["second"], ["third"] ];   

You have something like the second. You want something like the first.

Guys i used this : final.push(names[i].concat(parseFloat(values[i]*count[i]))) .
instead of this: final.push([names[i], values[i] * count[i]]). And it worked.
I still don’t get why my previous way didn’t work :confused: I mean, i kinda understand the array thing, i just don’t get why using push on [names[i], values[i] * count[i]] delivers something different if there’s a “,” between them and they are being pushed in the position togheter.

You could do exactly what you did (take the names elements as an array, and add the value to that array), or you could have the names as an array of strings and simply

var names = ['PENNY','NICKEL','DIME','QUARTER'];  // a simple array of strings

/* and later, you would */
final.push([ names[i] /*JUST THE STRING*/, values[i]*count[i] ]);

The ONLY thing wrong was, the test was looking for an array containing a string and a value, as a pair. You were returning an array containing another array with a string, and a value.

Simply changing that names array, by removing the nested [ ], would also have passed.