java多线程--生产者消费者模式三种实现

方法一、传统版

synchronized wait()notify() 方法实现:
资源类:

   public class Resource { 
           private int apple = 0;     
           public synchronized void increace() { //
               while (apple !=0) { 
                   try { 
                       wait(); 
                   } catch (InterruptedException e) { 
                       e.printStackTrace(); 
                   } 
                  
               } 
               apple++; 
               System. out .println("生成苹果成功!" );
               notify(); 
           }       
           public synchronized void decreace() { 
               while (apple ==0) { 
                   try { 
                       wait(); 
                   } catch (InterruptedException e) { 
                       e.printStackTrace(); 
                   } 
               } 
               apple--; 
              System. out.println( "消费苹果成功!" );
               notify(); 
           } 

测试:

public static void main(String[] args) {
		Box box=new Box();
		new Thread(new Runnable() {			
			@Override
			public void run() {
				// TODO Auto-generated method stub
			for(int i=1;i<=5;i++) {
				try {
					box.increace();
				} catch (Exception e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}
		 }
		},"AA").start();
		new Thread(new Runnable() {			
			@Override
			public void run() {
				// TODO Auto-generated method stub
			for(int i=1;i<=5;i++) {
				try {
					box.decreace();
				} catch (Exception e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}
		 }
		},"BB").start();
	     
	}
	

在这里插入图片描述
传统到2.0版本:
在这里插入图片描述

2.0版本:Condition和Lock

class ShareData{//资源类
	private int number=0;
	private Lock lock=new ReentrantLock();
	private Condition condition=lock.newCondition();
	
	public void increment()throws Exception {
		lock.lock();
		try {
			//1判断
			while(number!=0) {
				//等待,不能生产
				condition.await();
			}
			//2干活
			number++;
			System.out.println(Thread.currentThread().getName()+" \t "+number);
			//3通知唤醒
			condition.signalAll();
		}catch(Exception e) {
			e.printStackTrace();
		}finally {
			lock.unlock();
		}
	}
	
	public void decrement()throws Exception {
		lock.lock();
		try {
			//1判断
			while(number==0) {
				//等待,不能生产
				condition.await();
			}
			//2干活
			number--;
			System.out.println(Thread.currentThread().getName()+" \t "+number);
			//3通知唤醒
			condition.signalAll();
		}catch(Exception e) {
			e.printStackTrace();
		}finally {
			lock.unlock();
		}
	}
}

测试:

public static void main(String[] args)throws Exception {
		ShareData shareData=new ShareData();
		
		new Thread(new Runnable() {			
			@Override
			public void run() {
				// TODO Auto-generated method stub
			for(int i=1;i<=5;i++) {
				try {
					shareData.increment();
				} catch (Exception e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}
		 }
		},"AA").start();
		new Thread(new Runnable() {			
			@Override
			public void run() {
				// TODO Auto-generated method stub
			for(int i=1;i<=5;i++) {
				try {
					shareData.decrement();
				} catch (Exception e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}
		 }
		},"BB").start();
	}

在这里插入图片描述

3.0版本: BlockingQueue阻塞队列实现

class MyResource{
	private volatile boolean FLAG=true;//默认开启,进行生产消费
	private AtomicInteger atomicInteger=new AtomicInteger();
	
	BlockingQueue<String> blockingQueue=null;
	public MyResource(BlockingQueue<String> blockingQueue) {//构造方法注入,不写死用哪个阻塞队列实现
		this.blockingQueue=blockingQueue;
		System.out.println(blockingQueue.getClass().getName());
	}
	
	public void myProd()throws Exception {
		String data=null;
		boolean retValue;
		while(FLAG) {
			data=atomicInteger.incrementAndGet()+"";//加1操作
			retValue=blockingQueue.offer(data, 2L,TimeUnit.SECONDS);
			if(retValue) {
				System.out.println(Thread.currentThread().getName()+"\t 插入队列"+data+"成功");
			}else {
				System.out.println(Thread.currentThread().getName()+"\t 插入队列"+data+"失败");
			}
			TimeUnit.SECONDS.sleep(1);
		}
		System.out.println(Thread.currentThread().getName()+"\t 大老板叫停,表示FLAG=false,生产动作结束");
	}
	public void myConsumer()throws Exception {
		String result=null;
		while(FLAG) {
			result=blockingQueue.poll(2L,TimeUnit.SECONDS);
			if(null==result||result.equalsIgnoreCase("")) {//将此String 与另一个 String 进行比较,不考虑大小写。如果两个字符串的长度相等,并且两个字符串中的相应字符都相等(忽略大小写),则认为这两个字符串是相等的
				FLAG=false;
				System.out.println(Thread.currentThread().getName()+"\t 超过2秒钟没有取到蛋糕,消费退出");
				System.out.println();
				System.out.println();
				return;
			}
			System.out.println(Thread.currentThread().getName()+"\t 消费队列蛋糕"+result+"成功");
		}
	}

	public void stop() {
		// TODO Auto-generated method stub
		this.FLAG=false;
	}
}
public static void main(String[] args)throws Exception {
		
	MyResource myResource=new MyResource(new ArrayBlockingQueue<String>(10));
	
	new Thread(new Runnable() {
		public void run() {
			System.out.println(Thread.currentThread().getName()+"\t 生产线程启动");
			try {
				myResource.myProd();
			} catch (Exception e) {
				// TODO: handle exception
				e.printStackTrace();
			}
		}
	},"Prod").start();
	
	new Thread(new Runnable() {
		public void run() {
			System.out.println(Thread.currentThread().getName()+"\t消费线程启动");
			System.out.println();
			System.out.println();
			try {
				myResource.myConsumer();
				System.out.println();
				System.out.println();
			} catch (Exception e) {
				// TODO: handle exception
				e.printStackTrace();
			}
		}
	},"Consumer").start();
	
	try {TimeUnit.SECONDS.sleep(5);}catch(InterruptedException e){e.printStackTrace();}
	System.out.println();
	System.out.println();
	System.out.println();
	
	System.out.println("5秒钟时间到,大老板main叫停,活动结束");
	myResource.stop();
	}

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值