我尝试用ArrayList做生产者-消费者问题,有多个生产者,多个消费者,用wait、noitify、notifyAll做并发控制。
当生产者生产完毕后,如何只notify消费者呢?
黄舟2017-04-17 11:42:47
You make sure that only the consumer is waiting, so that notify will only notify the consumer.
By the way, why do you want the producer to wait?
Add a lock to the queue, and then create two Conditions, one is full, which handles the situation when the queue is full; the other is empty, which handles the situation when the queue is empty.
The operation process is as follows:
Producer:
1. Obtain lock
2. Check whether the queue is full. If it is full, wait for the full condition until awakened by the consumer
3. Add elements to the queue
4. notify empty condition, wake up a consumer
5. Release the lock
Consumer:
1. Obtain lock
2. Check whether the queue is empty. If it is empty, wait for the empty condition until awakened by the producer
3. Remove an element from the queue
4. notify full condition, wake up a producer
5. Release the lock.
Keep in mind that Condition is not a lock, and there is no "locking" of Condition.
伊谢尔伦2017-04-17 11:42:47
The thread awakened by notify is random, so there is usually no way to specify who is awakened.
Based on my level of knowledge, I think there are two ways to do it:
1. Set the priority of the consumer thread and use notifyAll to increase the probability of the consumer thread obtaining resources;
2. It is to ensure that after the producer finishes executing, only the consumer is waiting;
黄舟2017-04-17 11:42:47
class BoundedBuffer {
final Lock lock = new ReentrantLock();
final Condition notFull = lock.newCondition();
final Condition notEmpty = lock.newCondition();
final Object[] items = new Object[100];
int putptr, takeptr, count;
public void put(Object x) throws InterruptedException {
lock.lock();
try {
while (count == items.length)
notFull.await();
items[putptr] = x;
if (++putptr == items.length) putptr = 0;
++count;
notEmpty.signal();
} finally {
lock.unlock();
}
}
public Object take() throws InterruptedException {
lock.lock();
try {
while (count == 0)
notEmpty.await();
Object x = items[takeptr];
if (++takeptr == items.length) takeptr = 0;
--count;
notFull.signal();
return x;
} finally {
lock.unlock();
}
}
}
PHP中文网2017-04-17 11:42:47
The thread cannot be specified, notify will wake up a thread waiting for the object.
怪我咯2017-04-17 11:42:47
The thread cannot be specified, notify will wake up a thread waiting for the object.