Java多线程生产者消费者调度实现,java多线程,Java多线程生产者消费
分享于 点击 30609 次 点评:229
Java多线程生产者消费者调度实现,java多线程,Java多线程生产者消费
Java多线程生产者消费者调度实现
生产者消费者模型是多线程中最常见的模型,有着广泛的应用。其主要目的是实现一种动态的平衡,让生产者消费者和谐共处,获得最大化的执行效率。
所说的动态平衡其实就是生产者与消费者协作控制仓储,让消费者不至于缺货,也不能导致不合理不和谐的库存。
生产者消费者实现最简单的方式是通过java5之后的线程池来实现,下面的例子很粗糙,但是能良好运行。
在实际应用中,可以基于数据库,加上复杂逻辑,实现更强悍的后台处理程序,目前基于此模型构建的后台程序良好运行,处理效果极佳。
/** * 消费者 * * @author leizhimin 12-10-23 下午4:10 */ public class MyTask implements Runnable{ private long id; public MyTask(long id) { this.id = id; } @Override public void run() { try { Thread.sleep(100L); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("\t"+Thread.currentThread().getName()+":"+id); } }
import javax.swing.plaf.metal.MetalBorders; import java.util.concurrent.Executors; import java.util.concurrent.ThreadPoolExecutor; /** * 总调度程序 (包括协作生产) * * @author leizhimin 12-10-23 下午4:18 */ public class TaskPool extends Thread { private String poolname; private ThreadPoolExecutor pool = (ThreadPoolExecutor) Executors.newFixedThreadPool(5); public TaskPool(String poolname) { this.poolname = poolname; } @Override public void run() { System.out.println(poolname + ":池中的当前线程数getPoolSize()=" + pool.getPoolSize()); int i = 0; while(true){ int x = pool.getQueue().size(); // System.out.println("返回核心线程数="+pool.getCorePoolSize()); System.out.println("返回此执行程序使用的任务队列="+pool.getQueue().size()); if(x>=5) try { Thread.sleep(10L); continue; } catch (InterruptedException e) { e.printStackTrace(); } System.out.println(poolname + "该加入任务了"); //生产过程 for(int k =i+10;i<k;i++){ pool.submit(new MyTask(i)); } } } public static void main(String[] args) { new TaskPool("pool1").start(); } }
E:\jdk1.6.0_33\bin\java -Didea.launcher.port=7534 -Didea.launcher.bin.path=C:\IDEA11.1.3\bin -Dfile.encoding=UTF-8 -classpath E:\jdk1.6.0_33\jre\lib\charsets.jar;E:\jdk1.6.0_33\jre\lib\deploy.jar;E:\jdk1.6.0_33\jre\lib\javaws.jar;E:\jdk1.6.0_33\jre\lib\jce.jar;E:\jdk1.6.0_33\jre\lib\jsse.jar;E:\jdk1.6.0_33\jre\lib\management-agent.jar;E:\jdk1.6.0_33\jre\lib\plugin.jar;E:\jdk1.6.0_33\jre\lib\resources.jar;E:\jdk1.6.0_33\jre\lib\rt.jar;E:\jdk1.6.0_33\jre\lib\ext\dnsns.jar;E:\jdk1.6.0_33\jre\lib\ext\localedata.jar;E:\jdk1.6.0_33\jre\lib\ext\sunjce_provider.jar;E:\jdk1.6.0_33\jre\lib\ext\sunmscapi.jar;E:\jdk1.6.0_33\jre\lib\ext\sunpkcs11.jar;G:\testprojects\testpool\out\production\testpool;C:\IDEA11.1.3\lib\idea_rt.jar com.intellij.rt.execution.application.AppMain TaskPool pool1:池中的当前线程数getPoolSize()=0 返回此执行程序使用的任务队列=0 pool1该加入任务了 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 pool-1-thread-1:0 pool-1-thread-2:1 pool-1-thread-5:4 pool-1-thread-4:3 pool-1-thread-3:2 返回此执行程序使用的任务队列=0 pool1该加入任务了 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 pool-1-thread-1:5 pool-1-thread-5:7 pool-1-thread-2:6 pool-1-thread-3:9 pool-1-thread-4:8 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 pool-1-thread-1:10 返回此执行程序使用的任务队列=4 pool1该加入任务了 返回此执行程序使用的任务队列=14 pool-1-thread-5:11 pool-1-thread-4:14 pool-1-thread-3:13 pool-1-thread-2:12 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 pool-1-thread-1:15 pool-1-thread-4:17 pool-1-thread-3:18 pool-1-thread-2:19 pool-1-thread-5:16 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 pool-1-thread-1:20 pool-1-thread-2:23 pool-1-thread-5:24 pool-1-thread-3:22 pool-1-thread-4:21 返回此执行程序使用的任务队列=0 pool1该加入任务了 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 pool-1-thread-1:25 pool-1-thread-2:26 pool-1-thread-3:28 pool-1-thread-5:27 pool-1-thread-4:29 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 pool-1-thread-1:30 pool-1-thread-4:34 pool-1-thread-3:32 pool-1-thread-5:33 pool-1-thread-2:31 返回此执行程序使用的任务队列=0 pool1该加入任务了 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 pool-1-thread-1:35 pool-1-thread-4:36 pool-1-thread-3:37 pool-1-thread-2:39 pool-1-thread-5:38 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 pool-1-thread-1:40 pool-1-thread-5:44 pool-1-thread-2:43 pool-1-thread-3:42 pool-1-thread-4:41 返回此执行程序使用的任务队列=0 pool1该加入任务了 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10 pool-1-thread-1:45 pool-1-thread-2:47 pool-1-thread-3:48 pool-1-thread-5:46 pool-1-thread-4:49 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 返回此执行程序使用的任务队列=5 pool-1-thread-1:50 返回此执行程序使用的任务队列=4 pool1该加入任务了 返回此执行程序使用的任务队列=14 pool-1-thread-5:53 pool-1-thread-3:52 pool-1-thread-4:54 pool-1-thread-2:51 返回此执行程序使用的任务队列=10 返回此执行程序使用的任务队列=10。。。。。
可以看到,库存永远不会超过14。
用户点评