zoukankan      html  css  js  c++  java
  • java基础——线程通信机制,生产者消费者

    package communication;
    
    /*
    使用两个线程1,2交替打印1-100
    
    线程通信方法:
        1.wait():一旦执行此方法,当前线程进入阻塞态,并释放锁
        2.notify():会唤醒被wait的一个线程,如果有多个线程wait,则唤醒优先级高的
        3.notifyAll():唤醒所有被wait的线程
    
    说明:
        1.wait(),notify(),notifyAll()使用在同步代码块或同步方法中,不能用在lock方法中
        2.这三个方法的调用者必须是同步代码块或同步方法中的锁对象(同步监视器)
            否则会出现异常
        3.这三个方法定义在java.lang.Object 中
    
    sleep()和wait()的不同
    1.声明位置不同,Thread类汇总声明sleep,Object中声明wait
    2.sleep可以在任何需要场景调用,wait必须由同步监视器调用
    3.sleep后线程不释放锁,wait线程释放锁
    
    @author zsben
    @create 2020-01-05 12:05
    */
    
    import java.util.concurrent.locks.ReentrantLock;
    
    class Number implements Runnable{
    
        private int number = 100;
        private ReentrantLock lock = new ReentrantLock(false);
    
        @Override
        public void run() {
            while(true){
                synchronized (this){
                    //唤醒所有线程线程
                    notifyAll();
    
                    if(number > 0){
                        try {
                            //线程会阻塞,但是不会释放锁对象
                            Thread.sleep(100);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
    
                        try {
                            //使该线程进入阻塞态,同时释放持有的锁对象
                            wait();
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
    
                        System.out.println(Thread.currentThread().getName()+": "+number);
                        number--;
                    }else break;
                }
            }
        }
    }
    
    public class CommunicationTest {
        public static void main(String[] args) {
            Number number = new Number();
            Thread t1 = new Thread(number);
            Thread t2 = new Thread(number);
            Thread t3 = new Thread(number);
    
            t1.start();
            t2.start();
            t3.start();
        }
    }

    下面是生产者消费者的例子

    package communication;
    
    /*
    生产者消费者问题实现
    
    @author zsben
    @create 2020-01-05 13:55
    */
    
    class Clerk{
    
        private int productCount = 0;
    
        //生产产品:原子操作
        public synchronized void produceProduct() {
    
            if(productCount < 20){
                productCount++;
                System.out.println(Thread.currentThread().getName()+"生产产品"+productCount);
                notify();
            }
            else {
                try {
                    wait();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    
        //消费产品:原子操作
        public synchronized void consumerProduct() {
            if(productCount > 0){
                System.out.println(Thread.currentThread().getName()+"消费产品"+productCount);
                productCount--;
                notify();
            }
            else {
                try {
                    wait();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }
    class Producer extends Thread{
        private Clerk clerk;
    
        public Producer(Clerk clerk) {//生产者
            this.clerk = clerk;
        }
    
        @Override
        public void run() {
            System.out.println(getName()+": 开始生产产品...");
    
            while(true){
                try {
                    Thread.sleep(10);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
    
                clerk.produceProduct();
            }
        }
    }
    
    class Consumer extends Thread{//消费者
        private Clerk clerk;
    
        public Consumer(Clerk clerk) {
            this.clerk = clerk;
        }
    
        @Override
        public void run() {
            System.out.println(getName()+": 开始消费产品...");
    
            while(true){
                try {
                    Thread.sleep(10);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
    
                clerk.consumerProduct();
            }
        }
    }
    
    public class ProductTest {
    
        public static void main(String[] args) {
            Clerk clerk = new Clerk();
            Producer p1 = new Producer(clerk);
            p1.setName("生产者1");
            Consumer c1 = new Consumer(clerk);
            c1.setName("消费者1");
    
            p1.start();
            c1.start();
        }
    }
  • 相关阅读:
    mybatis 使用动态SQL
    mybatis 使用resultMap实现关联数据的查询(association 和collection )
    mybatis中的resultMap
    struts2 + ajax + json的结合使用,实例讲解
    destroy-method="close"的作用
    ajax
    Iterator<转>
    实现ajax
    struts返回json
    orm 相关
  • 原文地址:https://www.cnblogs.com/zsben991126/p/12153090.html
Copyright © 2011-2022 走看看