银行业务调度系统
模拟实现银行业务调度系统逻辑,具体需求如下:
Ø 银行内有6个业务窗口,1 - 4号窗口为普通窗口,5号窗口为快速窗口,6号窗口为VIP窗口。
Ø 有三种对应类型的客户:VIP客户,普通客户,快速客户(办理如交水电费、电话费之类业务的客户)。
Ø 异步随机生成各种类型的客户,生成各类型用户的概率比例为:
VIP客户 :普通客户 :快速客户 = 1 :6 :3。
Ø 客户办理业务所需时间有最大值和最小值,在该范围内随机设定每个VIP客户以及普通客户办理业务所需的时间,快速客户办理业务所需时间为最小值(提示:办理业务的过程可通过线程Sleep的方式模拟)。
Ø 各类型客户在其对应窗口按顺序依次办理业务。
Ø 当VIP(6号)窗口和快速业务(5号)窗口没有客户等待办理业务的时候,这两个窗口可以处理普通客户的业务,而一旦有对应的客户等待办理业务的时候,则优先处理对应客户的业务。
Ø 随机生成客户时间间隔以及业务办理时间最大值和最小值自定,可以设置。
Ø 不要求实现GUI,只考虑系统逻辑实现,可通过Log方式展现程序运行结果。
启动类
package heima.com.bankcallsystem; import heima.com.bankcallsystem.business.Test; public class App { public static void main(String[] args) { Test.start(); } }
模拟6个窗口和生成用户
package heima.com.bankcallsystem.business; import java.util.Random; import java.util.concurrent.Executors; import java.util.concurrent.ScheduledExecutorService; import java.util.concurrent.TimeUnit; import heima.com.bankcallsystem.manage.Constant; import heima.com.bankcallsystem.manage.CustomerType; import heima.com.bankcallsystem.manage.NumberGeneratorMachine; public class Test { static ScheduledExecutorService pool=Executors.newScheduledThreadPool(7); public static void start(){ generateUser(); generateWindow(); } private static void generateWindow() { int index=1; for(;index<5;index++){ final Window commonWindow=new Window(); commonWindow.setCustomerType(CustomerType.common); commonWindow.setWindowType(CustomerType.common); commonWindow.setWindowId(index); pool.scheduleAtFixedRate( new Runnable(){ @Override public void run() { commonWindow.calling(); if(commonWindow.isWork()){ commonWindow.work(); } } }, 0, 1, TimeUnit.SECONDS); } final Window fastWindow=new Window(); fastWindow.setCustomerType(CustomerType.fast); fastWindow.setWindowType(CustomerType.fast); fastWindow.setWindowId(index++); pool.scheduleAtFixedRate( new Runnable(){ @Override public void run() { fastWindow.calling(); if(fastWindow.isWork()){ fastWindow.work(); } } }, 0, 1, TimeUnit.SECONDS); final Window vipWindow=new Window(); vipWindow.setCustomerType(CustomerType.vip); vipWindow.setWindowType(CustomerType.vip); vipWindow.setWindowId(index); pool.scheduleAtFixedRate( new Runnable(){ @Override public void run() { vipWindow.calling(); if(vipWindow.isWork()){ vipWindow.work(); } } }, 0, 1, TimeUnit.SECONDS); } public static void generateUser(){ System.out.println("客户升请服务机启动。。。。"); pool.scheduleAtFixedRate( new Runnable(){ @Override public void run() { Random rd=new Random(); int type=rd.nextInt(10)+1; if(type==1){ CustomerType customerType=CustomerType.vip; generateUser(customerType,Constant.VIP_RATIO); }else if(type>1 && type<5){ CustomerType customerType=CustomerType.fast; generateUser(customerType,Constant.FAST_RATIO); }else{ CustomerType customerType=CustomerType.common; generateUser(customerType,Constant.COMMON_RATIO); } } private void generateUser(CustomerType customerType,long typeRatio) { try { Thread.currentThread().sleep(Constant.GENERATE_USER_INTERVAL_TIME*typeRatio); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } NumberGeneratorMachine numberMachine=NumberGeneratorMachine.getInstance(); numberMachine.setCustomerType(customerType); System.out.println(numberMachine.generateNumberManage().generateServiceNumber()+"号"+customerType+"客户升请服务"); } }, 0, 1, TimeUnit.MILLISECONDS); } }
银行的呼叫方法
package heima.com.bankcallsystem.business; import java.util.Random; import java.util.concurrent.Executors; import heima.com.bankcallsystem.manage.Constant; import heima.com.bankcallsystem.manage.CustomerType; import heima.com.bankcallsystem.manage.NumberGeneratorMachine; import heima.com.bankcallsystem.manage.NumberManage; public class Window { private CustomerType customerType=CustomerType.common; private CustomerType windowType=CustomerType.common; private int serviceNumber; private int windowId=1; private boolean isWork=true; public boolean isWork(){ return isWork; } public void setWindowId(int windowId) { this.windowId = windowId; System.out.println(this.windowId+"号"+customerType+"窗口打开"); } public void setWindowType(CustomerType windowType) { this.windowType = windowType; } public void setCustomerType(CustomerType customerType) { this.customerType = customerType; } public void calling(){ NumberGeneratorMachine numberMachine= NumberGeneratorMachine.getInstance(); numberMachine.setCustomerType(customerType); NumberManage numberManage=numberMachine.generateNumberManage(); numberManage.setWaitFlag(true); if(customerType==CustomerType.common && windowType!=CustomerType.common){ numberManage.setWaitFlag(false); } System.out.println(windowId+"号"+windowType+"窗口开始呼叫"+customerType+"用户"); serviceNumber=numberManage.fetchServiceNumber(); //如果没有vip和快速 为普通用户服务 if(serviceNumber==-1){ if(customerType==CustomerType.common){ try { System.out.println(windowId+"号"+windowType+"窗口没叫到普通顾客休息3秒钟 "); Thread.currentThread().sleep(3*1000); } catch (InterruptedException e) { e.printStackTrace(); } isWork=false; return; } this.customerType=CustomerType.common; calling(); //vip fast窗口为普通用户服务完在服务本类客户 customerType=windowType; return; } System.out.println(serviceNumber+"号"+customerType+"客户请到"+windowId+"号"+windowType+"窗口"); System.out.println(windowId+"号"+windowType+"窗口呼叫完毕"); //初始化调用work逻辑 isWork=true; } public void work() { System.out.println(windowId+"号"+windowType+"窗口正在为"+serviceNumber+"号"+customerType+"客户服务"); long beginTime=System.currentTimeMillis(); try { Thread.currentThread().sleep(new Random().nextInt(Constant.WORK_MAX_TIME-Constant.WORK_MIN_TIME+1)+Constant.WORK_MIN_TIME); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } long endTime=System.currentTimeMillis(); System.out.println(windowId+"号"+windowType+"窗口为"+serviceNumber+"号"+customerType+"客户服务完成 耗时"+(endTime-beginTime)/1000l+"s"); } }
常量
package heima.com.bankcallsystem.manage; public class Constant { //办理业务最短时间1S public final static int WORK_MIN_TIME=1*1000; //办理业务最长时间10S public final static int WORK_MAX_TIME=10*1000; //模拟生成用户的间隔时间 public final static int GENERATE_USER_INTERVAL_TIME=1*1000; //不通类型的比例 1:3:6 public final static int COMMON_RATIO=1; public final static int FAST_RATIO=3; public final static int VIP_RATIO=6; }
类型
package heima.com.bankcallsystem.manage; public enum CustomerType { common("普通"),fast("快速"),vip("vip"); private String alias; private CustomerType(String alias){ this.alias=alias; } @Override public String toString(){ return this.alias; } }
服务号码请求机
package heima.com.bankcallsystem.manage; public class NumberGeneratorMachine { private static NumberGeneratorMachine instance=null; private NumberManage commonNumberManage=null; private NumberManage fastNumberManage=null; private NumberManage vipNumberManage=null; private CustomerType customerType=CustomerType.common; public void setCustomerType(CustomerType customerType) { this.customerType = customerType; } public NumberManage generateNumberManage(){ NumberManage numberManage=null; switch(customerType){ case common: numberManage=commonNumberManage; break; case fast: numberManage=fastNumberManage; break; case vip: numberManage=vipNumberManage; break; } return numberManage; } private NumberGeneratorMachine(){ commonNumberManage=new NumberManage(CustomerType.common); fastNumberManage=new NumberManage(CustomerType.fast); vipNumberManage=new NumberManage(CustomerType.vip); } public static NumberGeneratorMachine getInstance(){ if(instance==null){ synchronized(NumberGeneratorMachine.class){ if(instance==null){ instance=new NumberGeneratorMachine(); } } } return instance; } }
号码管理---------------------- <a href="http://edu.csdn.net/heima" target="blank">android培训</a>、<a href="http://edu.csdn.net/heima" target="blank">java培训</a>、期待与您交流! ----------------------
package heima.com.bankcallsystem.manage; import java.util.ArrayList; import java.util.List; public class NumberManage { private int serviceNumber; private List<Integer> serviceNumbers; private CustomerType customerType; private boolean isWaitFlag=true; public void setWaitFlag(boolean isWaitFlag) { this.isWaitFlag = isWaitFlag; } NumberManage(CustomerType customerType){ serviceNumbers=new ArrayList<Integer>(); this.customerType=customerType; } public synchronized int generateServiceNumber(){ serviceNumbers.add(++serviceNumber); if(customerType==CustomerType.common){ notify(); } return serviceNumber; } public synchronized int fetchServiceNumber(){ int result=-1; if(serviceNumbers.isEmpty()){ if(customerType==CustomerType.common && isWaitFlag){ try { wait(); } catch (InterruptedException e) { e.printStackTrace(); } } } if(!serviceNumbers.isEmpty()){ result=serviceNumbers.remove(0); } return result; } }