本题主要难点有两部分:

1,找零算法。如何找零应该是最具技巧性的部分,根据已有的硬币金额分布,对应的解决办法可能会有不同。本题中的1,2,5,10这种情况满足贪心性质,故我们简单的用贪心算法的思想来解决。一般更加通用的是利用动态规划或者穷举,这个后面有机会会专门进行讨论。

2,代码业务逻辑。本题所描述的系统已经是一个较为完整的贩卖系统,更多地需要我们从整体上把握代码结构,明白个部分间的关系。如果初始感到无从下手,那么说明在较复杂情况下的编程能力还有欠缺,日后应继续练习。

由于临近入职比较忙,这里简单附上所有的源码,参考其中的注释应不难理解。

 import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Scanner;
import java.util.Stack; public class VendingSystem { static ArrayList<Product> products;//商品信息
static ArrayList<Coin> coins;//币盒信息
static int balance;//余额 public static void main(String[] args) {
String orders = getParas();
String[] orderArray = orders.split(";");
handleOrder(orderArray);
} /*
* 处理接收到的命令
*/
public static void handleOrder(String[] orderArray) {
char operation = ' ';
for (String order : orderArray) {
operation = order.charAt(0);
switch (operation) {
//初始化
case 'r':
initialize(order);
break;
//投币
case 'p':
dropCoin(order);
break;
//购买
case 'b':
buy(order);
break;
//退币
case 'c':
change(order);
break;
//查询
case 'q':
query(order);
break;
default:
break;
}
}
} /*
* 获取输入命令
*/
public static String getParas() {
Scanner reader = new Scanner(System.in);
String orders = reader.nextLine();
reader.close();
return orders;
} /*
* 初始化商品个数和钱币个数
*/
public static void initialize(String paras) {
int[] productPrice = {2, 3, 4, 5, 8, 6};
int[] coinValue = {1, 2, 5, 10};
String[] initializationData = paras.split(" ");
products = new ArrayList<Product>();
coins = new ArrayList<Coin>();
String[] productNum = initializationData[1].split("-");
for (int i = 0; i < productNum.length; i ++) {
products.add(new Product(("A" + (i + 1)), productPrice[i], Integer.parseInt(productNum[i])));
}
String[] coinNum = initializationData[2].split("-");
for (int j = 0; j < coinNum.length; j ++) {
coins.add(new Coin((coinValue[j] + " yuan coin"), coinValue[j], Integer.parseInt(coinNum[j])));
}
System.out.println("S001:Initialization is successful");
} /*
* 处理查询请求
*/
public static void query(String order) {
String[] queryPara = order.split(" ");
if (queryPara.length < 2 || (!queryPara[1].equals("0") && !queryPara[1].equals("1"))) {
System.out.println("E010:Parameter error");
return;
}
if (queryPara[1].equals("0")) {
int weight = 0;//weight用来保存每件商品的排序优先级,越大则优先级越高,注意weight是不会重复的
HashMap<Integer, Integer> weightAndIndexMap = new HashMap<Integer, Integer>();
int[] weights = new int[products.size()];
for (int i = 0; i < products.size(); i ++) {
weight = products.get(i).getNum() * 10 - i;
weights[i] = weight;
weightAndIndexMap.put(weight, i);
}
Arrays.sort(weights);
Product tempProduct = null;
for (int i = weights.length - 1; i >= 0; i --) {
tempProduct = products.get(weightAndIndexMap.get(weights[i]));
System.out.println(tempProduct.getName() + " " + tempProduct.getPrice() + " " + tempProduct.getNum());
} } else {
for (Coin coin : coins) {
System.out.println(coin.name + " number=" + coin.num);
}
}
} /*
* 处理投币
*/
public static void dropCoin(String order) {
String[] dropPara = order.split(" ");
//注意题目给的稍微有点问题,这里的判断确认参数为正整数
//投币金额
int dropValue = Integer.parseInt(dropPara[1]);
if (dropValue != 1 && dropValue != 2 && dropValue != 5 && dropValue != 10 && dropValue < 10) {
System.out.println("E002:Denomination error");
} else {
//钱盒中1, 2硬币总额
int temp = coins.get(0).getNum() * coins.get(0).getValue() +
coins.get(1).getNum() * coins.get(1).getValue();
if (temp < dropValue && dropValue != 1 && dropValue != 2) {
System.out.println("E003:Change is not enough, pay fail");
return;
}
if (Integer.parseInt(dropPara[1]) > 10) {
System.out.println("E004:Pay the balance is beyond the scope biggest");
return;
}
boolean isProductEmpty = true;
for (Product product : products) {
if (product.getNum() > 0) {
isProductEmpty = false;
break;
}
}
if (isProductEmpty) {
System.out.println("E005:All the goods sold out");
return;
} switch (dropValue) {
case 1:
coins.get(0).setNum(coins.get(0).getNum() + 1);
break;
case 2:
coins.get(1).setNum(coins.get(1).getNum() + 1);
break;
case 5:
coins.get(2).setNum(coins.get(2).getNum() + 1);
break;
case 10:
coins.get(3).setNum(coins.get(3).getNum() + 1);
break;
default:
break;
}
balance += dropValue;
System.out.println("S002:Pay success,balance=" + balance);
}
} /*
* 处理购买命令
*/
public static void buy(String order) {
String[] buyPara = order.split(" ");
HashMap<String, Integer> productNameAndIndexMap = new HashMap<String, Integer>();
for (int i = 0; i < products.size(); i ++) {
productNameAndIndexMap.put(products.get(i).getName(), i);
}
String productToBuy = buyPara[1];
if (productToBuy.equals("A1") || productToBuy.equals("A2") ||
productToBuy.equals("A3") ||productToBuy.equals("A4") ||
productToBuy.equals("A5") ||productToBuy.equals("A6")) {
Product tempProduct = products.get(productNameAndIndexMap.get(productToBuy));
if (tempProduct.getNum() == 0) {
System.out.println("E007:The goods sold out");
return;
}
if (tempProduct.getPrice() > balance) {
System.out.println("E008:Lack of balance");
return;
}
tempProduct.setNum(tempProduct.getNum() - 1);
balance -= tempProduct.getPrice();
System.out.println("S003:Buy success,balance=" + balance);
} else {
System.out.println("E006:Goods does not exist");
}
} /*
* 退钱找零
*/
public static void change(String order) {
if (balance == 0) {
System.out.println("E009:Work failure");
return;
}
int[] coinNums = new int[coins.size()];
for (int i = 0; i < coins.size(); i ++) {
coinNums[i] = coins.get(i).getNum();
}
findChange(coinNums, balance);
} /*
* 退币方法
*/
public static boolean findChange(int[] coinNums, int countToChange) {
if (countToChange < 1) {
return false;
}
int originalCount = countToChange;
boolean isFound = false;
Stack<Integer> coinStack = new Stack<Integer>();
Stack<Integer> changeStack = new Stack<Integer>();
for (int i = 0; i < coinNums.length; i ++) {
for (int j = 0; j < coinNums.length - i; j ++) {
for (int k = 0; k < coinNums[j]; k ++) {
switch (j) {
case 0:
coinStack.push(1);
break;
case 1:
coinStack.push(2);
break;
case 2:
coinStack.push(5);
break;
case 3:
coinStack.push(10);
break;
default:
break;
}
}
}
while (!coinStack.isEmpty()) {
int tempCoinValue = coinStack.pop();
if (countToChange >= tempCoinValue) {
countToChange -= tempCoinValue;
changeStack.push(tempCoinValue);
}
}
if (countToChange == 0) {
isFound = true;
break;
} else {
countToChange = originalCount;
coinStack.clear();
changeStack.clear();
}
}
if (isFound) {
balance = 0;
int[] changeResult = new int[coinNums.length];
while (!changeStack.isEmpty()) {
switch (changeStack.pop()) {
case 1:
changeResult[0] ++;
break;
case 2:
changeResult[1] ++;
break;
case 5:
changeResult[2] ++;
break;
case 10:
changeResult[3] ++;
break;
default:
break;
}
}
for (int i = 0; i < changeResult.length; i ++) {
coins.get(i).setNum(coins.get(i).getNum() - changeResult[i]);
switch (i) {
case 0:
System.out.println("1 yuan coin number=" + changeResult[i]);
break;
case 1:
System.out.println("2 yuan coin number=" + changeResult[i]);
break;
case 2:
System.out.println("5 yuan coin number=" + changeResult[i]);
break;
case 3:
System.out.println("10 yuan coin number=" + changeResult[i]);
break;
default:
break;
}
}
return true;
} else {
return findChange(coinNums, originalCount - 1);
}
}
}
class Product { String name;
int price;
int num; public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getPrice() {
return price;
}
public void setPrice(int price) {
this.price = price;
}
public int getNum() {
return num;
}
public void setNum(int num) {
this.num = num;
} public Product() { } public Product(String name, int price, int num) {
super();
this.name = name;
this.price = price;
this.num = num;
}
@Override
public String toString() {
return "Product [name=" + name + ", price=" + price + ", num=" + num + "]";
} }
class Coin { String name;
int value;
int num; public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getValue() {
return value;
}
public void setValue(int value) {
this.value = value;
}
public int getNum() {
return num;
}
public void setNum(int num) {
this.num = num;
}
public Coin() {
super();
}
public Coin(String name, int value, int num) {
super();
this.name = name;
this.value = value;
this.num = num;
}
@Override
public String toString() {
return "Coin [name=" + name + ", value=" + value + ", num=" + num + "]";
} }

华为OJ之自动售货系统的更多相关文章

  1. 语言模拟ATM自动取款机系统

    C语言实验报告       题目名称:C语言模拟ATM自动取款机系统 C语言模拟实现ATM自动取款机功能:输入密码,余额查询,取款,存款,转账,修改密码,退出功能: 代码实现的功能: 账号及密码输入: ...

  2. 艺萌文件上传下载及自动更新系统(基于networkComms开源TCP通信框架)

    1.艺萌文件上传下载及自动更新系统,基于Winform技术,采用CS架构,开发工具为vs2010,.net2.0版本(可以很容易升级为3.5和4.0版本)开发语言c#. 本系统主要帮助客户学习基于TC ...

  3. 自动升级系统OAUS的设计与实现(续) (附最新源码)

    (最新OAUS版本请参见:自动升级系统的设计与实现(续2) -- 增加断点续传功能) 一.缘起 自从 自动升级系统的设计与实现(源码) 发布以后,收到了很多使用者的反馈,其中最多的要求就是希望OAUS ...

  4. 华为OJ:火车进站

    火车进站 给定一个正整数N代表火车数量,0<N<10,接下来输入火车入站的序列,一共N辆火车,每辆火车以数字1-9编号.要求以字典序排序输出火车出站的序列号. 输入描述: 有多组测试用例, ...

  5. 京东商城招聘自动调价系统架构师 T4级别

    岗位级别:T4 岗位职责: 1.负责自动调价系统的架构设计 2.负责自动调价的预测.相关性算法设计 3.核心代码编写,代码review 任职要求: 1.熟悉数据挖掘.机器学习理论和算法 2.熟悉海量数 ...

  6. 在华为oj的两个月

    一次偶然的机会,我接触到华为oj平台(http://career-oj.huawei.com/exam/camLogin.jsp),当时的心情很是兴奋,于是立马注册开通,然后迫不及待地上去做题.刚开始 ...

  7. LINUX通过PXE自动部署系统

    原理介绍 TFTP(Trivial File Transfer Protocol,简单文件传输协议)是TCP/IP 协议族中的一个用来在客户机与服务器之间进行简单文件传输的协议,提供不复杂.开销不大的 ...

  8. 配置NTP网络时间自动校对系统时间和创建备份文件

    1 案例1:配置用户和组账号 1.1 问题 本例要求创建下列用户.组以及组的成员关系: 新建用户 alex,其用户ID为3456,密码是flectrag 创建一个名为 adminuser 的组 创建一 ...

  9. 自动驾驶系统 bfs

    一家科技公司有一块试验地用于测试自动驾驶系统.试验地由n×m个格子组成,从上到下依次编号为第1到n行,从左到右依次编号为第1到m列.试验车位于其中的某个格子上,每次自动驾驶系统可以控制汽车往上下左右移 ...

随机推荐

  1. asp.net core教程 (二)

    Asp.net Core环境设置 Asp.net Core环境设置 安装Microsoft Visual Studio 2015 Asp.Net Core是Asp.Net的一个重大的重新设计. 这个话 ...

  2. 移动端页面开发适配 rem布局原理

    主题 HTML移动端页面开发适配 rem布局原理 什么是适配,为什么要适配 我们拿到的设计图一般是以640,750,1080分辨率为基准设计的,而现在的手机终端各式各样,分辨率不同,逻辑像素不同 ,适 ...

  3. re 学习随便

    . 任意一个字符 \转义字符 *  字符重复0--多次 + 字符重复1-多次 ? 字符重复0-1次 ^行首匹配 或者在一个字符集中表示取反 \$  匹配字符串末尾 \b 匹配\w 与\w 之间的 \B ...

  4. centOS下服务启动

    nginx应该在mongodb之后启动,也可以通过chkconfig <服务名> on将服务设置为开机自启动.具体命令如下 service mysql start service memc ...

  5. logging模块

    要想使用好logging模块首先要知道它的使用流程: logging类的实例化:logger=logging.getLogger('') 设置logger的级别,logger.setLevel(log ...

  6. 关于数据库优化1——关于count(1),count(*),和count(列名)的区别,和关于表中字段顺序的问题

    1.关于count(1),count(*),和count(列名)的区别 相信大家总是在工作中,或者是学习中对于count()的到底怎么用更快.一直有很大的疑问,有的人说count(*)更快,也有的人说 ...

  7. JS键盘事件对象之keyCode、charCode、which属性对比

    先说一些有关键盘事件的事项:用js实现键盘记录,要关注浏览器的三种按键事件类型,即keydown,keypress和keyup,它们分别对应onkeydown. onkeypress和onkeyup这 ...

  8. java中的vo、dto 、dao

    VO是跟数据库里表的映射,一个表对应一个VO  DAO是用VO来访问真实的表,对数据库的操作都在DAO中完成  BO是业务层,做逻辑处理的 VO , PO , BO , QO, DAO ,POJO  ...

  9. 微服务架构:基于微服务和Docker容器技术的PaaS云平台架构设计(微服务架构实施原理)

    版权声明:本文为博主原创文章,转载请注明出处,欢迎交流学习! 基于微服务架构和Docker容器技术的PaaS云平台建设目标是给我们的开发人员提供一套服务快速开发.部署.运维管理.持续开发持续集成的流程 ...

  10. php导入csv文件

    <?php /** * Created by PhpStorm. * User: hanks * Date: 2017/4/30 * Time: 13:24 */ include 'header ...