我想使用Java中的生产者消费者模型将比赛条件复制到死锁中



在Wiki上,我找到了以下生产者 - 消费者程序的伪代码,该计划具有可能导致僵局的种族条件:

int itemCount = 0;
procedure producer() 
{
    while (true) 
    {
        item = produceItem();
        if (itemCount == BUFFER_SIZE) 
        {
            sleep();
        }
        putItemIntoBuffer(item);
        itemCount = itemCount + 1;
        if (itemCount == 1) 
        {
            wakeup(consumer);
        }
    }
}
procedure consumer() 
{
    while (true) 
    {
        if (itemCount == 0) 
        {
            sleep();
        }
        item = removeItemFromBuffer();
        itemCount = itemCount - 1;
        if (itemCount == BUFFER_SIZE - 1) 
        {
            wakeup(producer);
        }
        consumeItem(item);
    }
}

使用此实现,应发生以下情况:

  1. 消费者刚刚读取了变量ItemCount,注意到它为零,并且即将在IF块内移动。

  2. 在打电话睡眠之前,消费者被中断并恢复生产者。

  3. 生产者创建一个项目,将其放入缓冲区并增加Itemcount。

  4. 因为缓冲区在上次添加之前是空的,所以生产者试图唤醒消费者。

  5. 不幸的是,消费者尚未睡觉,并且唤醒电话丢失了。当消费者恢复时,它会入睡,再也不会唤醒。这是因为只有当itemcount等于1时,消费者才被生产者唤醒。

  6. 生产者将循环直到缓冲区饱满,之后它也将入睡。

我希望能够在Java中复制此功能,但是到目前为止,我在运行程序多次后无法进行。这是我的代码:

private LinkedList<Integer> sharedList = new LinkedList<Integer>();
private int sharedValue = 0;
private int MAX_LIMIT = 10;
public void produce() throws InterruptedException {
    Random random = new Random();
    while (true) {
        synchronized (this) {
            if (sharedValue == MAX_LIMIT) { //'produce' thread waits if list is full
                wait();
            }
            sharedValue = sharedValue + 1;
            sharedList.add(sharedValue); System.out.println("added value: " + sharedValue);
            if (sharedValue == 1) {
                notify(); //notifies  'consume' thread if list is not empty
            }
        }
    }
}
public void consume() throws InterruptedException {
    Random random = new Random();
    while (true) {
        synchronized (this) {
            if (sharedValue == 0) {    //'consume' waits if list is empty
                wait();
            }
            sharedValue = sharedValue - 1;
            sharedList.remove(); System.out.println("removed value: " + sharedValue);
            if (sharedValue == MAX_LIMIT-1) {
                notify(); //notifies 'produce' if list is not full
            }
        }
        Thread.sleep(random.nextInt(1000));
    }
}

原因是您同步整个迭代步骤。synchronized (this) {...}下的两个代码块将顺序运行。

您可以用:

复制它
    private LinkedList<Integer> sharedList = new LinkedList<Integer>();
    private volatile int sharedValue = 0;
    private int MAX_LIMIT = 10;
    public void produce() throws InterruptedException {
        while (true) {
            if (sharedValue == MAX_LIMIT) { //'produce' thread waits if list is full
                synchronized (this) {
                    wait();
                }
            }
            synchronized (this) {
                sharedValue = sharedValue + 1;
                sharedList.add(sharedValue);
                System.out.println("added value: " + sharedValue);
            }
            if (sharedValue == 1) {
                synchronized (this) {
                    notify(); //notifies  'consume' thread if list is not empty
                }
            }
        }
    }
    public void consume() throws InterruptedException {
        while (true) {
            if (sharedValue == 0) {    //'consume' waits if list is empty
                synchronized (this) {
                    wait();
                }
            }
            synchronized (this) {
                sharedValue = sharedValue - 1;
                sharedList.remove();
                System.out.println("removed value: " + sharedValue);
            }
            if (sharedValue == MAX_LIMIT - 1) {
                synchronized (this) {
                    notify(); //notifies 'produce' if list is not full
                }
            }
        }
    }

相关内容

  • 没有找到相关文章

最新更新