62,614
社区成员
发帖
与我相关
我的任务
分享
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
/**
* 收银台
* @author Administrator
*/
class Charge {
int number; // 编号
int type = 0; // 类型,0普通收银台,1培训收银台
List<Client> queue = new ArrayList<Client>(); // 排队的顾客
int lastGoodsNum = 0; // 最后一个顾客的商品数
private int nextTime = 0; // 下个顾客收费开始的时间
public Charge(int number) {
this.number = number;
}
/**
* 顾客加入队列
*
* @param client
*/
public void addClient(Client client) {
queue.add(client);
lastGoodsNum = client.goodsNum;
}
/**
* 到下一个顾客收费
*/
void nextClient() {
if (ChargeSystem.time == nextTime) { // 当前顾客收费完成,从队列中移除
if (queue.size() > 0) {
Client c = queue.get(0);
String chargeType = type == 0 ? "普通" : "培训";
System.out.print(chargeType + "收银机" + number + "完成一个" + c.type
+ "类顾客收费,");
int s = c.goodsNum * (type == 0 ? 1 : 2);
System.out.println("商品数:" + c.goodsNum + ",花费时间:" + s);
queue.remove(0);
if (queue.size() == 0)
lastGoodsNum = 0;
}
}
if (ChargeSystem.time >= nextTime) {
if (queue.size() > 0) { // 计算下一顾客需要的收费时长
// 培训机每件商品收费时候2分钟,普通机1分钟
nextTime = queue.get(0).goodsNum * (type == 0 ? 1 : 2);
nextTime += ChargeSystem.time;
}
}
}
}
/**
* 顾客抽象类
* 考虑顾客以后的扩展,不同顾客选择的收银台方式不台,所以抽象出一个类
* @author Administrator
*/
abstract class Client{
String type; //顾客类型
int arrival; // 到达时间
int goodsNum; // 商品数量
public Client(String type, int arrival, int goodsNum) {
this.type = type;
this.arrival = arrival;
this.goodsNum = goodsNum;
}
/**
* 根据顾客自己的喜好加入收银机的队列
*/
public abstract void joinQueue(List<Charge> charges);
/**
* 顾客选择收银台优先权
*/
public int compareTo(Client c){
if(goodsNum != c.goodsNum)
return goodsNum - c.goodsNum; //商品数量不一样的,数量少优先
return type.compareTo(c.type); //否则A类顾客优先
}
/**
* 创建顾客
*/
public static Client createClinet(String type, int arrival, int goodsNum){
if("A".equals(type)){
return new ClientA(arrival, goodsNum);
}else if("B".equals(type)){
return new ClientB(arrival, goodsNum);
}
return null;
}
}
/**
* A类顾客
*/
class ClientA extends Client {
public ClientA(int arrival, int goodsNum) {
super("A", arrival, goodsNum);
}
@Override
public void joinQueue(List<Charge> charges) {
int index = 0;
if (charges.size() > 1) {
for (int i = 0; i < charges.size() - 1; i++) { // A顾客排队总是选择人数最少的队
if (charges.get(i).queue.size() > charges.get(i + 1).queue.size())
index = i + 1;
}
}
charges.get(index).addClient(this);
System.out.println("A("+goodsNum+")顾客加入了收银台" + charges.get(index).number + "的队列");
}
}
/**
* B类顾客
*/
class ClientB extends Client {
public ClientB(int arrival, int goodsNum) {
super("B", arrival, goodsNum);
}
@Override
public void joinQueue(List<Charge> charges) {
int index = 0;
if (charges.size() > 1) {
for (int i = 0; i < charges.size() - 1; i++) { // B顾客排队总是选择 队末尾的那个人商品个数越少的队
if (charges.get(i).lastGoodsNum == 0) {
index = i;
break;
} else if (charges.get(i + 1).lastGoodsNum == 0) {
index = i + 1;
break;
} else {
if (charges.get(i).lastGoodsNum > charges.get(i + 1).lastGoodsNum)
index = i + 1;
}
}
}
charges.get(index).addClient(this);
System.out.println("B("+goodsNum+")顾客加入了收银台" + charges.get(index).number + "的队列");
}
}
/**
* @描述:实现一个商店收银
* @Author lnk
* @timer 2014年1月24日 上午11:53:35
*/
public class ChargeSystem {
static int time; //时间
private List<Charge> charges; //收银机队列
private List<Client> clients; //顾客们
/**
* 初始化收银台和顾客
*/
public void init(){
initCharges(2);
initClients();
}
/**
* 初始化收银台
* @param num
*/
private void initCharges(int num){
charges = new ArrayList<Charge>();
while(--num >= 0){
charges.add(0, new Charge(num + 1));
}
if(charges.size() > 0)
charges.get(charges.size() - 1).type = 1; //最后一台为培训机
}
/**
* 初始化顾客
*/
private void initClients(){
clients = new ArrayList<Client>();
clients.add(Client.createClinet("A",1,5));
clients.add(Client.createClinet("B",2,1));
clients.add(Client.createClinet("A",3,5));
clients.add(Client.createClinet("B",5,3));
clients.add(Client.createClinet("A",8,2));
clients.add(Client.createClinet("B",3,2));
clients.add(Client.createClinet("A",5,3));
}
/**
* 顾客选择收银台
* @param list
*/
public void selectCharge(List<Client> list){
//按顾客优先权排序
Collections.sort(list, new Comparator<Client>() {
@Override
public int compare(Client o1, Client o2) {
return o1.compareTo(o2);
}
});
for (Client client : list) {
client.joinQueue(charges);
}
}
/**
* 打印收银的顾客队列
*/
public void display(){
for (Charge charge : charges) {
System.out.print("收银机"+charge.number+"的队列:");
for (Client client : charge.queue) {
System.out.print(client.type + "(" + client.goodsNum + ") ");
}
System.out.println();
}
System.out.println();
}
public static void main(String[] arg){
ChargeSystem system = new ChargeSystem();
system.init();
time = 0;
int startTime = -1;
boolean quit = true;
do{
System.out.println("时间:"+time);
//找出到达收银台的顾客
List<Client> list = new ArrayList<Client>();
for (int i = system.clients.size() - 1; i >= 0; i--) {
if(system.clients.get(i).arrival == time){
if(startTime == -1) startTime = time; //记录第一个顾客到达时间
list.add(system.clients.get(i));
system.clients.remove(i);
}
}
//顾客按优先权选择收银台
system.selectCharge(list);
boolean isAllClear = true;
for(Charge c : system.charges){
c.nextClient();
if(c.queue.size() > 0) isAllClear = false;
}
system.display();
time++;
//如果所有客户已经去结算同时所以收银台已结算完成就退出程序
quit = !(isAllClear && system.clients.size() == 0);
}while(quit);{
System.out.println("完成,时间:" + (time - startTime));
}
}
}
时间:0
收银机1的队列:
收银机2的队列:
时间:1
A(5)顾客加入了收银机1的队列
收银机1的队列:A(5)
收银机2的队列:
时间:2
B(1)顾客加入了收银机2的队列
收银机1的队列:A(5)
收银机2的队列:B(1)
时间:3
B(2)顾客加入了收银机2的队列
A(5)顾客加入了收银机1的队列
收银机1的队列:A(5) A(5)
收银机2的队列:B(1) B(2)
时间:4
培训收银机2完成一个B类顾客收费,商品数:1,花费时间:2
收银机1的队列:A(5) A(5)
收银机2的队列:B(2)
时间:5
A(3)顾客加入了收银机2的队列
B(3)顾客加入了收银机2的队列
收银机1的队列:A(5) A(5)
收银机2的队列:B(2) A(3) B(3)
时间:6
普通收银机1完成一个A类顾客收费,商品数:5,花费时间:5
收银机1的队列:A(5)
收银机2的队列:B(2) A(3) B(3)
时间:7
收银机1的队列:A(5)
收银机2的队列:B(2) A(3) B(3)
时间:8
A(2)顾客加入了收银机1的队列
培训收银机2完成一个B类顾客收费,商品数:2,花费时间:4
收银机1的队列:A(5) A(2)
收银机2的队列:A(3) B(3)
时间:9
收银机1的队列:A(5) A(2)
收银机2的队列:A(3) B(3)
时间:10
收银机1的队列:A(5) A(2)
收银机2的队列:A(3) B(3)
时间:11
普通收银机1完成一个A类顾客收费,商品数:5,花费时间:5
收银机1的队列:A(2)
收银机2的队列:A(3) B(3)
时间:12
收银机1的队列:A(2)
收银机2的队列:A(3) B(3)
时间:13
普通收银机1完成一个A类顾客收费,商品数:2,花费时间:2
收银机1的队列:
收银机2的队列:A(3) B(3)
时间:14
培训收银机2完成一个A类顾客收费,商品数:3,花费时间:6
收银机1的队列:
收银机2的队列:B(3)
时间:15
收银机1的队列:
收银机2的队列:B(3)
时间:16
收银机1的队列:
收银机2的队列:B(3)
时间:17
收银机1的队列:
收银机2的队列:B(3)
时间:18
收银机1的队列:
收银机2的队列:B(3)
时间:19
收银机1的队列:
收银机2的队列:B(3)
时间:20
培训收银机2完成一个B类顾客收费,商品数:3,花费时间:6
收银机1的队列:
收银机2的队列:
完成,时间:20import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Scanner;
public class Main {
@SuppressWarnings("resource")
public static void main(String[] args) {
//获取控制台输入
//Sample:
//2
//A 1 5
//B 2 1
//A 3 5
//B 5 3
//A 8 2
//ctrl + z
Scanner scanner = new Scanner(System.in);
int count = scanner.nextInt();
World world = new World(count);
int num = 1;
List<Customer> list = new ArrayList<Customer>();
while(scanner.hasNext()){
Customer command = Customer.getCustomer(scanner.next().charAt(0), scanner.nextInt(), scanner.nextInt(), num++);
list.add(command);
}
Collections.sort(list); //排序,按到达时间,类型,携带商品来排
world.setCustomers(list);
System.out.println(String.format("output: 完成时间%1$smins。", world.run()));
}
}
import java.util.List;
/**
* 用户接口,定义用户的操作
*/
public abstract class Customer implements Comparable<Customer>{
/**
* 客户的商品数,初始值为0
*/
private int goods;
/**
* 顾客的到达时间,初始值为0
*/
private int time;
/**
* 客户所站的收银台,初始化为null
*/
private Checkstand checkstand;
private String name;
/**
* 构造方法
* @param goods 商品数
* @param time 到达时间
*/
protected Customer(int goods, int time, int name){
this.goods = goods;
this.time = time;
this.name = "#" + name;
}
/**
* 获取真实顾客的实例,由type决定真实顾客是哪种类型
* @param type 顾客类型
* @param goods 商品数
* @param time 到达时间
* @return 不同顾客类型的实例
*/
public static Customer getCustomer(char type,int time,int goods ,int name){
switch(type){
case 'A':case 'a':
return new CustomerA(goods, time, name);
case 'B':case 'b':
return new CustomerB(goods, time, name);
}
return null;
}
/**
* 商品数的getter
* @return 商品数
*/
public int getGoods() {
return goods;
}
/**
* 商品数的setter
* @param goods 商品数
*/
public void setGoods(int goods) {
this.goods = goods;
}
/**
* 顾客的到达时间的setter
* @return 顾客的到达时间
*/
public int getTime() {
return time;
}
/**
* 顾客的到达时间的getter
* @param time 顾客的到达时间
*/
public void setTime(int time) {
this.time = time;
}
/**
* 所属收银台的getter
* @return 所属收银台
*/
public Checkstand getCheckstand() {
return checkstand;
}
/**
* 所属收银台的setter
* @param checkstand 所属收银台
*/
public void setCheckstand(Checkstand checkstand) {
this.checkstand = checkstand;
if(null!=checkstand)
checkstand.addCustomers(this);
}
public String getName(){
return name;
}
public int getLeaveTime(){
return getCheckstand().getFirstLeaveTime();
}
public abstract char getType();
/**
* 顾客的选择策略
* @param checkstands 收银台序列
*/
public abstract boolean choose(List<Checkstand> checkstands);
@Override
public int compareTo(Customer o) {
if(time != o.time)
return time - o.time;
if(getType() != o.getType())
return getType() - o.getType();
if(goods != o.goods)
return goods - o.goods;
return 0;
}
}
import java.util.List;
/**
* 顾客A
*/
public class CustomerA extends Customer {
/**
* 构造方法
*/
public CustomerA(int goods, int time, int name){
super(goods, time, name);
}
/**
* 选择站哪队,A的策略为站人少的,我想傻子都会优先站没人的吧
*/
@Override
public boolean choose(List<Checkstand> checkstands) {
int min=-1;
Checkstand toStand = null;
for(Checkstand checkstand:checkstands){
int size = checkstand.getCustomers().size();
if(size==0){
setCheckstand(checkstand);
return true;
}
if(min < 0 || min > size){
min = size;
toStand = checkstand;
}
}
setCheckstand(toStand);
return false;
}
/**
* 返回顾客的类型字符
*/
public char getType(){
return 'A';
}
}
import java.util.List;
/**
* 顾客B
*/
public class CustomerB extends Customer {
/**
* 构造方法
*/
public CustomerB(int goods, int time, int name){
super(goods, time, name);
}
/**
* 顾客B的选择策略:站最后那个拿的东西少的,同样肯定站没人的队
*/
@Override
public boolean choose(List<Checkstand> checkstands) {
int min = -1;
Checkstand toStand = null;
for(Checkstand checkstand:checkstands){
int size = checkstand.getCustomers().size();
if(size==0){
setCheckstand(checkstand);
return true;
}
int count = checkstand.getGoodsOfLastCustomer();
if(min < 0 || min > count){
min = count;
toStand = checkstand;
}
}
setCheckstand(toStand);
return false;
}
/**
* 返回顾客的类型字符
*/
public char getType(){
return 'B';
}
}
import java.util.LinkedList;
import java.util.Queue;
/**
* 定义收银台的接口
*/
public class Checkstand {
/**
* 剩余顾客的队列
*/
private Queue<Customer> customers;
/**
* 最后一名顾客的商品数
*/
private int goodsOfLastCustomer;
/**
* 每个商品的点算时间
*/
private int timeOfCounting;
/**
* 收银台编码
*/
private int num;
/**
* 该 收银台最后一次送顾客的时间
*/
private int lastLeaveTime;
/**
* 构造函数,默认点算时间为1
*/
public Checkstand(int num){
customers = new LinkedList<Customer>();
timeOfCounting = 1;
this.num = num;
}
/**
* 构造函数,指定点算时间
* @param timeOfCounting 点算时间
*/
public Checkstand(int timeOfCounting, int num){
this(num);
this.timeOfCounting = timeOfCounting;
}
/**
* 顾客队列的getter
* @return 顾客队列
*/
public Queue<Customer> getCustomers() {
return customers;
}
/**
* 获得最后那个顾客的商品数
* @return 最后那个顾客的商品数
*/
public int getGoodsOfLastCustomer() {
return goodsOfLastCustomer;
}
/**
* 设置最后那个顾客的商品数
* @param goodsOfLastCustomer 最后那个顾客的商品数
*/
public void setGoodsOfLastCustomer(int goodsOfLastCustomer) {
this.goodsOfLastCustomer = goodsOfLastCustomer;
}
/**
* 添加一名顾客,同时更新最后一名顾客的商品数量
* @param customer 新增顾客队列
*/
public void addCustomers(Customer customer) {
this.customers.add(customer);
this.goodsOfLastCustomer = customer.getGoods();
}
public int getNum(){
return num;
}
/**
* 送别顾客
*/
public void sendCustomer(){
lastLeaveTime = getFirstLeaveTime();
Customer customer = getCustomers().poll();
if(null!=customer){
System.out.println(String.format("t=%1$s : Customer %2$s 离开%3$s号收银台。", lastLeaveTime, customer.getName(), this.getNum()));
customer.setCheckstand(null);
}
}
/**
* 获得第一个顾客离开的时间
* @return 第一个顾客离开的时间
*/
public int getFirstLeaveTime(){
Customer customer = customers.peek();
if(null != customer && lastLeaveTime<customer.getTime()){
lastLeaveTime = customer.getTime();
}
if(null != customer){
return lastLeaveTime + customer.getGoods() * timeOfCounting;
}
return lastLeaveTime;
}
}
import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
import java.util.SortedSet;
import java.util.TreeSet;
/**
* 客观世界,模拟时间的流逝,顾客选择队列,顾客离开等客观现实
*/
public class World {
/**
* 队头的顾客
*/
private SortedSet<Customer> customers;
/**
* 所有顾客
*/
private List<Customer> allCustomer;
/**
* 所有的收银台
*/
private List<Checkstand> checkstands;
/**
* 最后一名顾客离开的时间,即处理完的时间
*/
private int leaveTime;
/**
* 世界构造器,初始化世界的变量
* @param count 收银台的个数
*/
public World(int count){
customers = new TreeSet<Customer>(new Comparator<Customer>() {
@Override
public int compare(Customer o1, Customer o2) {
if(o1.getCheckstand().getFirstLeaveTime()!=o2.getCheckstand().getFirstLeaveTime())
return o1.getCheckstand().getFirstLeaveTime() - o2.getCheckstand().getFirstLeaveTime();
else
return o1.getCheckstand().getNum() - o2.getCheckstand().getNum();
}
});
checkstands = new ArrayList<Checkstand> ();
for(int i=0;i<count-1;i++){
checkstands.add(new Checkstand(i+1));
}
checkstands.add(new Checkstand(2, count));
System.out.println(String.format("t=0: %1$s个收银台, 培训收银台是%1$s号", count));
}
/**
* 新来一位顾客
* @param customer 添加新顾客
*/
private void customerIncome(Customer customer){
//新增顾客时先看在这名顾客到达前是否有离开收银台的顾客
while(!customers.isEmpty() && customers.first().getCheckstand().getFirstLeaveTime() <= customer.getTime()){
sendCustomer();
}
if(customer.choose(checkstands)){
customers.add(customer);
}
System.out.println(String.format("t=%1$s : Customer %2$s %5$s 到达, %3$s个商品,去%4$s号收银台", customer.getTime(), customer.getName(), customer.getGoods(), customer.getCheckstand().getNum(), customer.getType()));
}
/**
* 计算完成的时间
* @return
*/
public int run(){
for(Customer customer: allCustomer){
customerIncome(customer);
}
while(!customers.isEmpty()){
sendCustomer();
}
return leaveTime;
}
/**
* 送离顾客,每当一位顾客离开,调用一次
*/
private void sendCustomer(){
Customer toSend = customers.first();
Checkstand checkstand = toSend.getCheckstand();
leaveTime = checkstand.getFirstLeaveTime();
customers.remove(toSend);
checkstand.sendCustomer();
if(null != checkstand.getCustomers().peek()){
customers.add(checkstand.getCustomers().peek());
}
}
/**
* 将排好序的顾客设置好
* @param customers 已排序的顾客列表
*/
public void setCustomers(List<Customer> customers){
this.allCustomer = customers;
}
}
本身很简单的题目,不过因为要求OOD,所以代码有点长,不过OOD也有好处,假设需要增加顾客类型或者收银台类型,可以很容易拓展package com.armslee.test.model;
import java.io.Serializable;
public class Customer implements Serializable{
private static final long serialVersionUID = 5934650144340059385L;
private String type;
private int arriveTime;
private int goodsCount;
/**
* 需要为这个顾客服务的总时间
*/
private int needHandleTime = -1;
public Customer() {
}
public Customer(String type,int t,int c){
this.type = type;
this.arriveTime = t;
this.goodsCount = c;
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
public int getArriveTime() {
return arriveTime;
}
public void setArriveTime(int arriveTime) {
this.arriveTime = arriveTime;
}
public int getGoodsCount() {
return goodsCount;
}
public void setGoodsCount(int goodsCount) {
this.goodsCount = goodsCount;
}
public int getNeedHandleTime() {
return needHandleTime;
}
public void setNeedHandleTime(int needHandleTime) {
this.needHandleTime = needHandleTime;
}
}
CashierDesk.java
package com.armslee.test.body;
import java.io.Serializable;
import java.util.Iterator;
import java.util.LinkedList;
import com.armslee.test.model.Customer;
public class CashierDesk implements Serializable{
private static final long serialVersionUID = 4398752666847665193L;
/**
* 每一个收银台用一个链表来存放顾客,
* 每一个顾客都放在一个链表中,
* 并且相同时间到的顾客放在同一个链表中
*/
private LinkedList<LinkedList<Customer>> cashierDesk;
/**
* 每个收银台的顾客数量
*/
private int cashierDeskCount;
/**
* 最后一次添加顾客到此收银台的时间
*/
private int lastAddTime = 0;
/**
* 初始化收银台
*/
public CashierDesk(){
cashierDesk = new LinkedList<LinkedList<Customer>>();
}
/**
* 添加顾客到此收银台队尾
*
* @param c 顾客信息
* @return
*/
public boolean addCustomer(Customer c){
LinkedList<Customer> linkedList = this.cashierDesk.peekLast();
if(null != linkedList && linkedList.peekLast().getArriveTime() == c.getArriveTime()){
Iterator<Customer> ite = linkedList.iterator();
int index = 0;
while(ite.hasNext()){
Customer cite = ite.next();
if(cite.getGoodsCount()>c.getGoodsCount()){//时间一样,商品数少的优先
break;
}
index ++;
}
if(index == linkedList.size()){//时间和商品数都一样,A类优先B类
index = 0;
if("B".equals(c.getType())){//B类直接放到最后面
linkedList.addLast(c);
}else{
Iterator<Customer> ite2 = linkedList.iterator();
while(ite2.hasNext()){
Customer cite = ite2.next();
if("A".equals(cite.getType())){//时间一样,商品数少的优先
index ++;
}else{
break;
}
}
}
}
linkedList.add(index, c);
}else{
LinkedList<Customer> temp = new LinkedList<Customer>();
temp.add(c);
this.cashierDesk.add(temp);
}
this.cashierDeskCount++;
this.lastAddTime = c.getArriveTime();
return true;
}
/**
* 获取该收银台最后一个顾客信息
*
* @return
*/
public Customer peekLast(){
LinkedList<Customer> linkedList = this.cashierDesk.peekLast();
if(null != linkedList && !linkedList.isEmpty()){
return linkedList.peekLast();
}
return null;
}
/**
* 获取该收银台第一个顾客的信息并删除顾客信息
*
* @return
*/
public Customer poll(){
LinkedList<Customer> linkedList = this.cashierDesk.peek();
Customer c = null;
if(null != linkedList){
c = linkedList.poll();
}
cashierDeskCount--;
if(linkedList.isEmpty()){
this.cashierDesk.poll();//删除已经没有顾客的队列
}
return c;
}
/**
* 获取该收银台第一个顾客的信息但不删除顾客信息
*
* @return
*/
public Customer peek(){
LinkedList<Customer> linkedList = this.cashierDesk.peek();
if(null != linkedList && !linkedList.isEmpty()){
return linkedList.peek();
}
return null;
}
public LinkedList<LinkedList<Customer>> getCashierDesk() {
return cashierDesk;
}
public void setCashierDesk(LinkedList<LinkedList<Customer>> cashierDesk) {
this.cashierDesk = cashierDesk;
}
public int getCashierDeskCount() {
return cashierDeskCount;
}
public void setCashierDeskCount(int cashierDeskCount) {
this.cashierDeskCount = cashierDeskCount;
}
public int getLastAddTime() {
return lastAddTime;
}
public void setLastAddTime(int lastAddTime) {
this.lastAddTime = lastAddTime;
}
}
CashierDeskConfig.java
package com.armslee.test.body;
import java.util.List;
import com.armslee.test.model.Customer;
public class CashierDeskConfig {
/**
* 收银台数组
*/
private static CashierDesk[] cashierDesk;
/**
* 收银台数目
*/
private static int cashierDeskNum;
/**
* 当前处理时间
*/
private static int currentTime = 0;
/**
* 非实习收银台处理一件商品的时间
*/
public final static int TIME_ONE = 1;
/**
* 实习收银台处理一件商品的时间
*/
public final static int TIME_TWO = 2;
public CashierDeskConfig() {
}
/**
* 初始化收银台数组
*
* @param deskNum
*/
public CashierDeskConfig(int deskNum){
cashierDeskNum = deskNum;
cashierDesk = new CashierDesk[cashierDeskNum];
for(int i =0 ;i<cashierDeskNum;i++){
cashierDesk[i] = new CashierDesk();
}
}
/**
* 每来一个顾客刷新一次收银台顾客的排队情况
*
* @return
*/
public void refreshCashierDesk(int arriveTime){
for(int i=0;i<cashierDeskNum;i++){
//当前刷新时刻需要处理的时间(分钟)
int needHandleTime = arriveTime - currentTime;
//标记是否处理完成,如果没有则继续处理
boolean done = false;
while(!done){
//取出该收银台上的第一个顾客
Customer c = cashierDesk[i].peek();
//该收银台没有顾客,直接退出
if(null == c){
break;
}
if(c.getNeedHandleTime() < needHandleTime){//处理当前顾客需要的时间小于当前时刻需要进行处理的时间
cashierDesk[i].poll();
needHandleTime -= c.getNeedHandleTime();
//当前处理的时刻
int nowCurrentTime = currentTime + c.getNeedHandleTime();
Customer cc = cashierDesk[i].peek();
if(null == cc){
break;
}
//下一个顾客到达的时间在前一个顾客处理完之后
if(cc.getArriveTime()> nowCurrentTime){
//两个顾客到达的间隙时间超过了当前还需要处理的时间
if((cc.getArriveTime() - nowCurrentTime) >= needHandleTime){
done = true;
}else{
needHandleTime -= (cc.getArriveTime() - nowCurrentTime);
}
}
}else if(c.getNeedHandleTime() == needHandleTime){
cashierDesk[i].poll();
done = true;
}else if(c.getNeedHandleTime() > needHandleTime){
c.setNeedHandleTime(c.getNeedHandleTime() - needHandleTime);
done = true;
}
}
}
currentTime = arriveTime;
}
/**
*
* 计算所有收银台在排好队并没有新的顾客加进来时完成收款的时间,选取最大值保存,将
* 其与排队处理时已经花费的时间就是整个收银需要的最大时间
*
* @return
*/
public int calculateTime(){
int t = 0;
for(int i=0;i<cashierDeskNum;i++){
int tt = 0;
while(cashierDesk[i].getCashierDeskCount()>0){
Customer c = cashierDesk[i].poll();
tt += c.getNeedHandleTime();
}
if(tt > t){
t = tt;
}
}
return t + currentTime;
}
/**
* 添加顾客到收银台上
*
* @param c
* @return
*/
public void addCustomerByList(List<Customer> c){
for (Customer customer : c) {
refreshCashierDesk(customer.getArriveTime());
int index = checkCashierDesk(customer.getType());
if(index == cashierDeskNum-1){
customer.setNeedHandleTime(customer.getGoodsCount()*TIME_TWO);
}else{
customer.setNeedHandleTime(customer.getGoodsCount()*TIME_ONE);
}
cashierDesk[index].addCustomer(customer);
}
}
/**
* 为顾客找一个合适的收银台等待付款
*
* @param customerType
* @return
*/
private int checkCashierDesk(String customerType){
if(cashierDesk[0].getCashierDeskCount() == 0){//第一个收银台还没有顾客
return 0;
}
int index = 0;
if("A".equals(customerType)){//A类顾客,选择人数最少的收银台
for(int i=1;i<cashierDeskNum;i++){
int s1 = cashierDesk[i].getCashierDeskCount();
int s2 = cashierDesk[i-1].getCashierDeskCount();
if(s1 == 0){//除了第一个收银台以外有一个没有顾客的收银台并且第一个收银台有顾客
index = i;
return index;
}
if( s1< s2){
index = i;
}
}
}else{//B类顾客,选择队尾顾客商品数最少的收银台
for(int i=1;i<cashierDeskNum;i++){
Customer c1 = cashierDesk[i].peekLast();
Customer c2 = cashierDesk[i-1].peekLast();
if(null == c1){//除了第一个收银台以外有一个没有顾客的收银台并且第一个收银台有顾客
index = i;
return index;
}
if(c1.getGoodsCount() < c2.getGoodsCount()){
index = i;
}
}
}
return index;
}
}
Cashier.java
package com.armslee.test;
import java.util.ArrayList;
import java.util.List;
import com.armslee.test.body.CashierDeskConfig;
import com.armslee.test.model.Customer;
public class Cashier {
public static void main(String[] args) {
CashierDeskConfig cdf = new CashierDeskConfig(2);
Customer c1 = new Customer("A",1,3);
Customer c2 = new Customer("B",1,5);
Customer c3 = new Customer("A",3,1);
Customer c4 = new Customer("B",4,1);
Customer c5 = new Customer("A",4,1);
List<Customer> clist = new ArrayList<Customer>();
clist.add(c1);
clist.add(c2);
clist.add(c3);
clist.add(c4);
clist.add(c5);
cdf.addCustomerByList(clist);
System.out.println("*********************************Lavender****************************");
System.out.println("完成收银时间为: "+cdf.calculateTime()+" mins");
System.out.println("*********************************Lavender****************************");
}
}
运行结果:
*********************************Lavender****************************
完成收银时间为: 13 mins
*********************************Lavender****************************