我的生产者/消费者解决方案正确吗

时间:2013-06-08 14:19:09

标签: java multithreading thread-safety producer-consumer

我正在尝试更多地了解线程,并认为提出解决生产者/消费者问题的解决方案将是一个良好的开端。我对解决方案的一个限制是,消费者并不提前知道生产者生产了多少。代码按预期运行,我运行了很多次,但这并不意味着它没有缺陷。这个解决方案有问题吗?

package Multithreading.ProducerConsumer;

import java.util.LinkedList;
import java.util.concurrent.Semaphore;

public class ProducerConsumer
{
    private class Producer implements Runnable
    {
        @Override
        public void run()
        {
            for(int i = 0; i < 1000; i++)
            {
                try 
                {
                    canProduce.acquire();
                    mutex.acquire();
                    queue.add(i);
                    mutex.release();
                    canConsume.release();
                } 
                catch (InterruptedException ex) 
                {
                    ;
                }
            }
            try
            {
                canConsume.acquire();
                isTryingToFinish = true;
                canConsume.release();
            }
            catch (InterruptedException ex)
            {
                ;
            }
        }
    }

    private class Consumer implements Runnable
    {
        @Override
        public void run()
        {
            while(!isDone)
            {
                try
                {
                    canConsume.acquire();
                    mutex.acquire();
                    System.out.println(queue.pop());
                    if(isTryingToFinish && queue.isEmpty())
                    {
                        isDone = true;
                    }
                    mutex.release();
                    canProduce.release();
                }
                catch (InterruptedException ex)
                {
                    ;
                }
            }
        }
    }

    Semaphore canProduce;
    Semaphore canConsume;
    Semaphore mutex;
    boolean isTryingToFinish = false;
    boolean isDone = false;
    final static int bufferSize = 100;
    LinkedList<Integer> queue;

    public ProducerConsumer()
    {
        queue = new LinkedList<>();
        canProduce = new Semaphore(bufferSize);
        canConsume = new Semaphore(0);
        mutex = new Semaphore(1);
    }

    public void Go() throws InterruptedException
    {
        Thread p = new Thread(new Producer());
        Thread c = new Thread(new Consumer());
        p.start();
        c.start();
        p.join();
        c.join();
        System.out.println("Job Complete!");
    }

    public static void main(String[] args) throws InterruptedException
    {
        ProducerConsumer p = new ProducerConsumer();
        p.Go();
    }
}

1 个答案:

答案 0 :(得分:0)

您可以查看MSDN's 'Example 2: Synchronizing two threads: a producer and a consumer'。这是c#,但这应该不是问题。