模拟生产者和消费者
1、使用“多线程&锁”模拟生产者和消费者
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 | class ShareData { private int number = 0 ; private Lock lock = new ReentrantLock(); private Condition condition = lock.newCondition(); public void increment() throws Exception { lock.lock(); try { //多线程的判断必须要用while while (number != 0 ) { //释放当前锁,进入等待状态,不能生产 //唤醒线程从await()返回后需要重新获得锁 condition.await(); } //生产 number++; System.out.println(Thread.currentThread().getName() + "\t" + number); //通知唤醒所有等待线程 condition.signalAll(); } catch (InterruptedException e) { e.printStackTrace(); } finally { lock.unlock(); } } public void decrement() throws Exception { lock.lock(); try { //多线程的判断必须要用while while (number != 1 ) { //释放当前锁,进入等待状态,不能消费 //唤醒线程从await()返回后需要重新获得锁 condition.await(); } //消费 number--; System.out.println(Thread.currentThread().getName() + "\t" + number); //通知唤醒所哟等待线程 condition.signalAll(); } catch (InterruptedException e) { e.printStackTrace(); } finally { lock.unlock(); } } } public class ProducerConsumer { public static void main(String[] args) { ShareData shareData = new ShareData(); new Thread(()->{ for ( int i = 0 ; i < 10 ; i++) { try { shareData.increment(); } catch (Exception e) { e.printStackTrace(); } } }, "A" ).start(); new Thread(()->{ for ( int i = 0 ; i < 10 ; i++) { try { shareData.decrement(); } catch (Exception e) { e.printStackTrace(); } } }, "B" ).start(); } } |
2、使用“多线程&阻塞队列”模拟生产者和消费者
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 | class ShareResource { //默认开启,进行生产+消费 private volatile boolean FLAG = true ; private AtomicInteger atomicInteger = new AtomicInteger(); BlockingQueue<String> blockingQueue = null ; public ShareResource(BlockingQueue<String> blockingQueue) { this .blockingQueue = blockingQueue; System.out.println(blockingQueue.getClass().getName()); } public void produce() throws InterruptedException { String data = null ; boolean retValue; while (FLAG) { data = atomicInteger.incrementAndGet() + "" ; 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() + "\tFLAG=false,生产结束" ); } public void consume() throws InterruptedException { String data = null ; while (FLAG) { data = blockingQueue.poll(2L, TimeUnit.SECONDS); if ( null == data || data.equalsIgnoreCase( "" )) { FLAG = false ; System.out.println(Thread.currentThread().getName() + "\t 超过2秒钟没有取到数据,消费退出" ); System.out.println(); return ; } System.out.println(Thread.currentThread().getName() + "\t消费数据" + data + "成功" ); } } public void stop() { this .FLAG = false ; } } public class ProducerAndConsumer { public static void main(String[] args) throws InterruptedException { ShareResource shareResource = new ShareResource( new ArrayBlockingQueue<String>( 10 )); new Thread(() -> { System.out.println(Thread.currentThread().getName() + "生产线程启动" ); try { shareResource.produce(); } catch (InterruptedException e) { e.printStackTrace(); } }, "Producer" ).start(); new Thread(() -> { System.out.println(Thread.currentThread().getName() + "消费线程启动" ); try { shareResource.consume(); } catch (InterruptedException e) { e.printStackTrace(); } }, "Consumer" ).start(); TimeUnit.SECONDS.sleep( 5 ); System.out.println( "5秒钟时间到,活动结束" ); shareResource.stop(); } } |
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 单元测试从入门到精通
· winform 绘制太阳,地球,月球 运作规律
· 上周热点回顾(3.3-3.9)