多线程学习使用(一)——仿真之银行业务系统
2016-10-23 15:09
330 查看
声明:文章内容全都是自己的学习总结,如有不对的地方请大家帮忙指出。有需要沟通交流的可加我QQ群:425120333 接下来的三篇都是关于学习了多线程之后的应用,参考的都是《java编程思想》这本书里的关于多线程仿真篇的内容。只是自己理解了后,重新打了一遍, 说真的,学习java光看是没什么用的,我一开始看书中的内容的时候,基本没看懂是什么意思,我跟着代码模仿着敲了一遍,在这过程中我也考虑了为啥要这样写。 这样等你一遍下来后,你就懂了80%左右了,然后你在自己不看再敲一遍,碰到不会的再看下,整个流程弄完了,再在纸上画下整个基本流程。这时你就懂了99%了, 剩下的1%你再练习一两遍就差不多了,仅仅只是看看,效果真的不大。 废话就说到这,接下来看下代码:
import java.util.LinkedList; import java.util.PriorityQueue; import java.util.Queue; import java.util.Random; import java.util.concurrent.ArrayBlockingQueue; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.TimeUnit; public class BankTellerPractice { public static void main(String[] args) { ExecutorService service = Executors.newCachedThreadPool(); CustomerLine line = new CustomerLine(50); service.execute(new GenrCustomer(line)); new TellerManager(service, line); try { TimeUnit.SECONDS.sleep(7); } catch (InterruptedException e) { e.printStackTrace(); } service.shutdownNow(); } } class Customer { private static int count = 0; private final int id = count++; private final int serviceTime; public Customer(int serviceTime) { this.serviceTime = serviceTime; } public int getServiceTime() { return serviceTime; } @Override public String toString() { return "Customer_" + id; } } class CustomerLine extends ArrayBlockingQueue<Customer> { private static final long serialVersionUID = 1L; public CustomerLine(int capacity) { super(capacity); } @Override public String toString() { if (this.size() == 0) { return "[Empty]"; } StringBuilder sb = new StringBuilder(); sb.append("[ "); for (Customer c : this) { sb.append(c); sb.append(" "); } sb.append("] "); return sb.toString(); } } class GenrCustomer implements Runnable { CustomerLine line; Random random = new Random(); public GenrCustomer(CustomerLine line) { this.line = line; } @Override public void run() { try { while (!Thread.interrupted()) { TimeUnit.MILLISECONDS.sleep(random.nextInt(300)); line.put(new Customer(random.nextInt(500))); } } catch (InterruptedException e) { System.out.println("模拟顾客来办理业务被打断 。。。。"); } System.out.println("模拟顾客来办理业务结束!!!"); } } class Teller implements Comparable<Teller>, Runnable { private static int count = 0; private final int id = count++; private boolean serviceCustomer = true; private int serviceNum = 0; CustomerLine line; public Teller(CustomerLine line) { this.line = line; } @Override public void run() { try { while (!Thread.interrupted()) { Customer customer = line.take(); TimeUnit.MILLISECONDS.sleep(customer.getServiceTime()); synchronized (this) { serviceNum++; if (!serviceCustomer) { wait(); } } } } catch (InterruptedException e) { System.out.println(this + ",业务员服务被打断 。。。。"); } System.out.println(this + " ,业务员已经离开!!!"); } public synchronized void doOtherThing() { serviceCustomer = false; serviceNum = 0; } public synchronized void serviceCustomer() { serviceCustomer = true; notify(); } @Override public int compareTo(Teller teller) { return serviceNum > teller.serviceNum ? 1 : (serviceNum == teller.serviceNum ? 0 : -1); } @Override public String toString() { return "Teller_" + id; } } class TellerManager implements Runnable { private PriorityQueue<Teller> workerQueue = new PriorityQueue<Teller>(); private Queue<Teller> doOtherThingQueue = new LinkedList<Teller>(); ExecutorService service; CustomerLine line; public TellerManager(ExecutorService service, CustomerLine line) { this.service = service; this.line = line; Teller teller = new Teller(line); workerQueue.add(teller); service.execute(teller); service.execute(this); } @Override public void run() { try { while (!Thread.interrupted()) { TimeUnit.MILLISECONDS.sleep(1000); adJust(); System.out.println(line + " { "); for (Teller teller : workerQueue) { System.out.println(teller + " "); } System.out.println("}"); } } catch (InterruptedException e) { System.out.println("业务员管理系统被打断。。。"); } System.out.println("业务员管理系统结束!!!"); } private void adJust() { if (line.size() / workerQueue.size() > 2) { if (doOtherThingQueue.size() > 0) { Teller teller = doOtherThingQueue.remove(); teller.serviceCustomer(); workerQueue.add(teller); } else { Teller teller = new Teller(line); workerQueue.add(teller); service.execute(teller); } return; } if (line.size() / workerQueue.size() < 2) { if (workerQueue.size() > 1) { signalTeller(); } } if (line.size() == 0) { while (workerQueue.size() > 1) { signalTeller(); } } } private void signalTeller() { Teller teller = workerQueue.remove(); teller.doOtherThing(); doOtherThingQueue.add(teller); } }
控制台输出:
[ Customer_5 ] {
Teller_0
}
[ Customer_7 Customer_8 Customer_9 Customer_10 Customer_11 Customer_12 Customer_13 ] {
Teller_1
Teller_0
}
[ Customer_14 Customer_15 Customer_16 Customer_17 Customer_18 ] {
Teller_1
Teller_0
}
[ Customer_24 ] {
Teller_0
}
[ Customer_27 ] {
Teller_0
}
[ Customer_32 Customer_33 ] {
Teller_1
Teller_0
}
[ Customer_36 Customer_37 Customer_38 ] {
Teller_0
}
[ Customer_42 Customer_43 Customer_44 ] {
Teller_1
Teller_0
}
业务员管理系统被打断。。。
业务员管理系统结束!!!
Teller_0,业务员服务被打断 。。。。
模拟顾客来办理业务被打断 。。。。
模拟顾客来办理业务结束!!!
Teller_1,业务员服务被打断 。。。。
Teller_1 ,业务员已经离开!!!
Teller_0 ,业务员已经离开!!!
从输出中可以看到达到了想要的效果,这些代码我都没加注释,只是希望大家能自己练习,实在弄不懂了可以联系我,我可以帮你解释下。
相关文章推荐
- 多线程学习使用(二)——仿真之饭店服务系统
- 学习使用SkyEye仿真(转)
- 使用 QEMU 进行系统仿真
- 学习《基于MATLAB/Simulink的系统技术与仿真》1
- UNIX环境高级编程学习之第十五章进程间通信 - 系统V 共享内存使用(使用信号灯保护共享内存)
- 使用 QEMU 进行系统仿真
- 收藏:学习使用SkyEye仿真
- IPHONE 多线程使用学习笔记
- Java6学习笔记60——多线程编程——使用volatile保障原子性
- 学习使用SkyEye仿真
- (转)[EntLib]微软企业库5.0 学习之路——第十步、使用Unity解耦你的系统—PART1——为什么要使用Unity?
- 学习摸索 Oracle数据库系统使用经验六则
- 多线程学习-使用临界区进行线程同步--发布日期:2008-07-17 16:38
- 学习使用SkyEye仿真[2005年08月03日更新]
- linux_vim编辑器的使用学习,按李先静老师的系统程序员
- linux学习使用总结-linux系统的安装和与windows双系统共享,linux常用的基本命令,今天贴在这里和大家分享
- SmartClient学习(四):使用多线程创建高响应智能客户端应用程序
- 使用 QEMU 进行系统仿真
- Java写的手机计费系统(作为学习参考的实例:关键是Java类库里面的date和Calendar的使用和相互转换,以及一些日期的实际问题)
- C#中使用try catch对系统性能的影响和处理机制的学习总结!