function checkCashRegister(price, cash, cid) {
var change;
var sumCid = 0; // Here is your change, ma'am. //找零(change),付款(cash),购买价格(price),收银机中零钱(cid)
change = cash - price; //计算零钱总额
for (var i = 0; i < cid.length; i++) {
sumCid += cid[i][1];
}
return sumCid;
sumCid = Number(sumCid.toFixed(2)); //保留两位小数 if (sumCid < change) {
return "Insufficient Funds"; //余额不足
} else if (sumCid === change) {
return "Closed";
} else {
// 1.零钱不够,返回余额不足
// 2.零钱足够,找回零钱
return overChange(change, cid, sumCid);
}
} function overChange(change, arr, sumCid) {
var array = [];
var len = arr.length; for (var i = len - 1; i >= 0; i--) {
if (arr[i][1] === 0) continue; if (arr[i][1] < change) {
array.push(arr[i]);
change -= arr[i][1];
change = Number(change.toFixed(2));
} else if (arr[i][1] > change) {
var x = arr[i][0]; // 取得零钱名称
var y = 0; switch(x) {
case "ONE HUNDRED":
y = Math.floor(change / 100) * 100;
break;
case "TWENTY":
y = Math.floor(change / 20) * 20;
break;
case "TEN":
y = Math.floor(change / 10) * 10;
break;
case "FIVE":
y = Math.floor(change / 5) * 5;
break;
case "ONE":
y = Math.floor(change / 1);
break;
case "QUARTER":
y = Math.floor(change / 0.25) * 0.25;
break;
case "DIME":
y = Math.floor(change / 0.10) * 0.10;
break;
case "NICKEL":
y = Math.floor(change / 0.05) * 0.05;
break;
case "PENNY":
y = Math.floor(change / 0.01) * 0.01;
break;
} if (y === 0 && sumCid - arr[i][1] < change) {
  return "Insufficient Funds";
} else if (y === 0) {
continue;
} else {
if (y < 1) {
y = y;
}
var array1 = [];
array1.push(arr[i][0]);
array1.push(y);
array.push(array1);
change -= y;
change = Number(change.toFixed(2));
}
}
} if (change === 0) {
return array;
} else {
return "Insufficient Funds";
} }

题目:

  设计一个收银程序 checkCashRegister() ,其把购买价格(price)作为第一个参数 , 付款金额 (cash)作为第二个参数, 和收银机中零钱 (cid) 作为第三个参数.

cid 是一个二维数组,存着当前可用的找零.

当收银机中的钱不够找零时返回字符串 "Insufficient Funds". 如果正好则返回字符串 "Closed".

否则, 返回应找回的零钱列表,且由大到小存在二维数组中.

分析:

  一个模拟找钱的程序。思路应该是这样的:

  首先,分析函数的参数,第一个参数是商品价格price,第二参数是支付现金金额cash,第三个是柜员机当前的零钱cid,是一个二维数组,它已经将所拥有的相同面值的钱币做了一个累加,比如面值为5元的就剩35元了这样。

  然后我们来分析函数的实现逻辑,结账时,会先扫描一下商品的价格,做一个累加,得到总的支付金额比如说78元,然后你给的钱是现金的话是不是要给50+20+5+1*3或者10*7+1*8等等等的组合。

  //找零(change),付款(cash),购买价格(price),收银机中零钱(cid)
change = cash - price;

但是你刚好没有零钱,最小100,你只能给100。那么此时基于交易等价交换的原则,柜员机得找零对吧,而且得找得回这么多零钱对吧,找不回就返回字符串"Insufficient Funds",表示零钱不足,交易基于等价交换的原则无法进行。那么你要先求找零的金额大小,然后与柜员机当前的零钱总额作比较。找零的金额为 cash - price,当前柜员机的零钱总额为各个面值大小的纸币的金额总额相加。数组是规律的,第一项是钱币面值,第二项是该面值的钱币总额。所以可以循环遍历叠加金额。

//计算零钱总额
for (var i = 0; i < cid.length; i++) {
sumCid += cid[i][1];
}

当可以找零的时候,你会拿钱,而且是一个面值的纸币一个面值的纸币的拿吧,不会找27元你找个27个一元钱吧。最简便的做法总是先给一张较大的但小于当前需要找零的零钱的纸币。这是使用循环变量递减的原因。

 for (var i = len - 1; i >= 0; i--) {

你没找零多少钱需要找得零钱总额在减小

change -= y;

还有一种情况就是,有可能柜员机零钱总额足够找零,但是找不开,比如说要找零3元,但你最小的纸币只剩下5元了,这时也是需要返回字符串"Insufficient Funds",表示零钱不足,交易基于等价交换的原则无法进行。

  if (y === 0 && sumCid - arr[i][1] < change) {
return "Insufficient Funds";
}
if (change === 0) {
return array;
} else {
return "Insufficient Funds";
}

change == 0 是判断能否成功找零的直接标准。

如果循环结束了,change != 0,说明现在的零钱找不开。否则返回需要找回的零钱。

方法参考文档

  

  Number.prototype.toFixed()

    toFixed() 方法使用定点表示法来格式化一个数。

    https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Number/toFixed

  

Exact Change FreeCodeCamp的更多相关文章

  1. Exact Change(背包HDU2753)

    Exact Change Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total ...

  2. FCC高级编程篇之Exact Change

    Exact Change Design a cash register drawer function checkCashRegister() that accepts purchase price ...

  3. Exact Change(01背包)

    描述 Seller: That will be fourteen dollars. Buyer: Here's a twenty. Seller: Sorry, I don't have any ch ...

  4. Exact Change

    设计一个收银程序 checkCashRegister() ,其把购买价格(price)作为第一个参数 , 付款金额 (cash)作为第二个参数, 和收银机中零钱 (cid) 作为第三个参数. cid ...

  5. [Advanced Algorithm] - Exact Change

    题目 设计一个收银程序 checkCashRegister(),其把购买价格(price)作为第一个参数 , 付款金额 (cash)作为第二个参数, 和收银机中零钱 (cid) 作为第三个参数. ci ...

  6. UVA-11517 Exact Change(DP)

    题目大意:有n张钞票,面值可能不同.你要买一件东西,可能需要找零钱.问最少付多少钱,并求出最少的钞票张数. 题目分析:定义状态dp(i,w)表示前i张钞票凑成w元需要的最少钞票张数.则状态转移方程为d ...

  7. FCC(ES6写法) Exact Change

    设计一个收银程序 checkCashRegister() ,其把购买价格(price)作为第一个参数 , 付款金额 (cash)作为第二个参数, 和收银机中零钱 (cid) 作为第三个参数. cid  ...

  8. FreeCodeCamp 高级算法(个人向)

    freecodecamp 高级算法地址戳这里. freecodecamp的初级和中级算法,基本给个思路就能完成,而高级算法稍微麻烦了一点,所以我会把自己的解答思路写清楚,如果有错误或者更好的解法,欢迎 ...

  9. Codeforces Round #598 (Div. 3) A. Payment Without Change 水题

    A. Payment Without Change You have a coins of value n and b coins of value 1. You always pay in exac ...

随机推荐

  1. Python-Pandas简单操作

    1.直接构建复杂嵌套索引 2. MultiIndex方式构建复杂的索引 多层索引操作 pandas堆叠处理

  2. 如何使用qtp12 utf进行功能测试

    首先,按照本博客的安装教程走的,右键管理员运行 接下来点击继续,这个界面只需要勾选到web即可 点击ok,开始运行 进入到主界面之后,file新建一个测试. 可以修改路径等等 点击create之后,出 ...

  3. 第一次训练 密码:acmore

    #include <cstdio> #include <cstring> #define M 100010 #define INF 0x7FFFFFFF #define Min ...

  4. jvm学习-ClassLoader(二)

    ClassLoader结构 jdk加载的4个步骤 CustomClassLoader 用户自定义的classLoader APPClassLoader主要加载classPath下面的class Ext ...

  5. mysql 的load data infile

    LOAD DATA INFILE语句从一个文本文件中以很高的速度读入一个表中.如果指定LOCAL关键词,从客户主机读文件.如果LOCAL没指定,文件必须位于服务器上.(LOCAL在MySQL3.22. ...

  6. POJ 1106

    先判断是否在圆内,然后用叉积判断是否在180度内.枚举判断就可以了... 感觉是数据弱了.. #include <iostream> #include <cstdio> #in ...

  7. Macserver服务更新经常使用的几个shell命令

    Macserver须要先开启远程登录.开启方式:系统偏好设置->共享 勾选远程登录 经常使用命令有: 拷贝(把本机文件复制到远程server上) scp -r 本地路径/file userNam ...

  8. Swift学习——变量var和let常量的用法(一)

    Swift中的变量var和let常量 首先介绍一下Swift中的 var 和 let (1)var 是 variable的缩写形式,是变量的意思 ,是可改变的.并非数据类型 比如: 注意每一个语句后面 ...

  9. luogu2261 [CQOI2007] 余数之和

    题目大意 求 \[\sum_{i=1}^{n}(k\mod i)\] \(n,k\leq 10^9\). 题解 先只考虑\(n\leq k\)的情况. \[\sum_{i=1}^{n}(k\mod i ...

  10. Node.js:工具模块

    ylbtech-Node.js:工具模块 1.返回顶部 1. Node.js 工具模块 在 Node.js 模块库中有很多好用的模块.接下来我们为大家介绍几种常用模块的使用: 序号 模块名 & ...