多个线程执行多个任务,解决该问题的死锁问题

之前我们说过的生产者消费者问题,当然是最简单的那种

/*
一个生产线程,一个消费线程,程序不存在安全问题

两个生产线程,两个消费线程,出现了生产两次,消费一次或生产一次消费两次的问题
出现问题的原因是:线程被唤醒之后没有回去判断标记,直接执行后边的代码
解决方式: 让线程被唤醒之后不是直接执行后边的代码,而是回去判断标记
           把if改成whileif改成while出现了死锁:原因是唤醒的是本方线程,导致所有线程全部等待
          notify唤醒的是任意一个线程,不能保证唤醒的是对方线程

          解决方式:把notify()改为notifyAll()
*/

代码演示的是正确的打开方式

//描述产品
class Product
{
   private String name;
   private int count;
   private boolean flag;

   //生产产品的功能
   public synchronized void produce(String name)
    {
        while(flag)
        {          
            try{wait();}catch(InterruptedException e){e.printStackTrace();}
        }
        this.name = name+"..."+count;
        System.out.println(Thread.currentThread().getName()+"生产了....."+this.name);
        count++;
        flag = true;
        notifyAll();
    }
  //消费产品的功能
  public synchronized void consume()
    {
        while(!flag)
        {
            try{wait();}catch(InterruptedException e){e.printStackTrace();}
        }
        System.out.println(Thread.currentThread().getName()+"......消费了....."+name);
        flag = false;
        notifyAll();
    }
}


//生产任务
class Producer implements Runnable
{
    private Product pro;
    public Producer(Product pro)
    {
        this.pro =pro;
    }
    public void run()
    {
        while(true)
        {
            pro.produce("笔记本");
        }
    }
}
//消费任务
class Consumer implements Runnable
{ 
    private Product pro;
    public Consumer(Product pro)
    {
        this.pro =pro;
    }
    public void run()
    {
        while(true)
        {
            pro.consume();
        }
    }
}
class Demo3 
{
    public static void main(String[] args) 
    {
        Product pro = new Product();

        Producer producer =new Producer(pro);
        Consumer consumer = new Consumer(pro);

        Thread t0 = new Thread(producer);
        Thread t1 = new Thread(producer);

        Thread t2 =  new Thread(consumer);
        Thread t3 =  new Thread(consumer);

        t0.start();
        t1.start();

        t2.start();
        t3.start();


    }
}

我们为了解决因为wait()而导致的死锁,我们选择唤醒所有进程,但是这种方法很低效,影响代码执行效率。
在下面的文章我们选择显示锁来解决这个问题。

你可能感兴趣的:(java基础)