简体   繁体   中英

Java lock's condition implementation

Need help with code at below link as it should run indefinitely likewise with any typical producer/consumer problem but somehow it is getting stuck on call of condition.signal(). What am I doing wrong here?

In main method, I have created two thread, one is consumer and other one is producer. it has shared task queue where both updates the entry.

package com.anurgup.handson;

import java.util.PriorityQueue;
import java.util.Queue;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

public class ConditionService implements Runnable {

    Lock lock = new ReentrantLock();
    Condition added = lock.newCondition();
    Condition removed = lock.newCondition();

    // type of service
    String type;

    // shared task for insertion and deletion of task
    static Queue<Integer> task = new PriorityQueue<Integer>();

    // max number of task allowed
    private static final int MAX_SIZE = 5;

    public ConditionService(String type) {
        this.type = type;
    }

    public static void main(String[] args) {

        ExecutorService service = Executors.newFixedThreadPool(2);
        service.submit(new ConditionService("producer"));
        service.submit(new ConditionService("consumer"));

    }

    public void produce() {
        try {
            while (true) {
                System.out.println("in producer...");
                synchronized (task) {
                    while (task.size() == MAX_SIZE)
                        removed.await();
                    System.out.println("added item: " + task.size());
                    task.add(task.size());
                    added.signal();
                }
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

    public void consume() {
        try {
            while (true) {
                System.out.println("in consumer...");
                synchronized (task) {
                    while (task.isEmpty())
                        added.await();
                    System.out.println("removed item: " + task.peek());
                    task.remove();
                    removed.signal();
                }
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void run() {
        if (this.type.equals("producer"))
            this.produce();
        else
            this.consume();
    }
}

You're making two mistakes. First, your lock and conditions need to be static, or each task will only synchronize and wait on itself. Second, you need to use lock.lock() , not synchronized . It should look like this:

lock.lock();
try {
    // wait
    // produce/consume
} finally {
    lock.unlock();
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM