zoukankan      html  css  js  c++  java
  • java多线程-线程间协作

    大纲:

    1. wait、notify、notifyAll
    2. Condition
    3. 生产消费者

    一、wait、notify、notifyAll

    1. wait、notify、notifyAll是Object的本地final方法。
    2. 在一个线程中调用object.wait()可以使当先线程阻塞并交出锁(object)。
    3. 既然obj.wait操作会交出锁,那必然在synchronized(obj)代码块内,且2个obj为统一对象。
    4. 使用obj.notify()能够唤醒任意一个等待obj锁的线程,obj.notifyAll()能够唤醒所有等待obj锁的线程。同样notify操作也必须在synchronized(obj)代码块内。
    5. 线程等待是锁对象的方法而不是线程的方法,试想在多个synchronized嵌套代码块内,调用wait()是不是应该指定释放哪一个锁对象。

    二、Condition

    1. Condition接口依赖于Lock接口,可以通过lock.newCondition() 。
    2. wait,notify操作都是控制一个锁下面的线程。Condition可以将一个锁下面的线程分成多种情况分别控制。
    3. 调用Condition的await()和signal()方法也需要在lock()-unlock()代码块内。
    4. Condition接口的await对应Object的wait方法 ,signal对应notify方法 ,signalAll对应notifyAll方法 。
    5. 使用Condition也更加高效。
    6. void awaitUninterruptibly():不响应中断的await方法。
    7. long awaitNanos(long nanosTimeout) throws InterruptedException:await上增加超时响应,返回值=nanosTimeout-消耗时间。

    三、生产消费者

    生产者、消费者线程轮流执行,操作同一个资源。

    消费者:

    public class Comsumer implements Runnable {
        Resource resource;
        public Comsumer(Resource resource){
            this.resource = resource;
        }
        @Override
        public void run() {
            try {
                resource.comsume();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

    生产者:

    public class Producer implements Runnable {
        Resource resource;
        public Producer(Resource resource){
            this.resource = resource;
        }
        @Override
        public void run() {
            try {
                resource.produce();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

    资源对象-wait,notify实现:

    public class Resource {
    
        private int r = 0;
        private Object lock = new Object();
        private boolean produced = false;
    
        public  void produce() throws InterruptedException {
            synchronized(lock){
                while (true){
                    while (produced){
                        lock.wait();
                    }
                    r++;
                    System.out.println(Thread.currentThread().getName()+"线程成产1个,当前剩余:"+r);
                    produced = true;
                    lock.notifyAll();
                }
            }
    
        }
    
        public void comsume() throws InterruptedException {
            synchronized(lock){
                while (true){
                    while (!produced){
                        lock.wait();
                    }
                    r--;
                    System.out.println(Thread.currentThread().getName()+"线程消费1个,当前剩余:>>"+r);
                    produced = false;
                    lock.notifyAll();
                }
            }
    
        }
    }

    资源对象-condition实现:

    public class Resource {
    
        private int r = 0;
        private boolean produced = false;
        Lock lock = new ReentrantLock();
        Condition proCondition = lock.newCondition();
        Condition comCondition = lock.newCondition();
    
        public  void produce() throws InterruptedException {
            lock.lock();
            try {
                while (true){
                    while (produced){
                        proCondition.await();
                    }
                    r++;
                    System.out.println(Thread.currentThread().getName()+"线程成产1个,当前剩余:"+r);
                    produced = true;
                    comCondition.signal();
                }
            }finally {
                lock.unlock();
            }
    
        }
    
        public void comsume() throws InterruptedException {
            lock.lock();
            try {
                while (true){
                    while (!produced){
                        comCondition.await();
                    }
                    r--;
                    System.out.println(Thread.currentThread().getName()+"线程消费1个,当前剩余:>>"+r);
                    produced = false;
                    proCondition.signal();
                }
            }finally {
                lock.unlock();
            }
    
        }
    }

     测试类

    class TestWait {
        public static void main(String[] args) {
            Resource r = new Resource();
            Producer producer = new Producer(r);
            Comsumer comsumer = new Comsumer(r);
            new Thread(producer).start();
            new Thread(producer).start();
            new Thread(producer).start();
            new Thread(comsumer).start();
            new Thread(comsumer).start();
            new Thread(comsumer).start();
        }
    }
  • 相关阅读:
    Django ORM常用的函数以及修饰词
    通过gitlabAPI批量创建用户
    【BZOJ】ARC083 E
    【Atcoder】ARC083 D
    【BZOJ】1604: [Usaco2008 Open]Cow Neighborhoods 奶牛的邻居
    【BZOJ】1593: [Usaco2008 Feb]Hotel 旅馆
    【BZOJ】5010: [Fjoi2017]矩阵填数
    【Atcoder】ARC082 E
    【BZOJ】5028: 小Z的加油店
    【BZOJ】1691: [Usaco2007 Dec]挑剔的美食家
  • 原文地址:https://www.cnblogs.com/liuboyuan/p/10368991.html
Copyright © 2011-2022 走看看