Чтобы понять, как работает Multi Threading, я использую Queue и ReentrantLock для моделирования проблемы производителя и потребителя. Мой поток производителя добавляет данные в очередь, но потребитель не удаляет. Я не уверен, правильно ли я это сделал. Я понимаю, что это уже было задано, но они не помогают.Потребитель-производитель с использованием ReentrantLock и Queue
пакет параллелизма;
import java.util.Queue;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;
class Producer implements Runnable{
Queue<Integer> list;
Condition con;
ReentrantLock lock;
int size;
Producer(Queue q1, Condition con, ReentrantLock l1,int size)
{
this.list=q1;
this.con=con;
this.lock=l1;
this.size=size;
}
public void run()
{
for(int i =0;i<20;i++)
{
if(lock.tryLock())
{
while(list.size()==size)
{
try
{
con.await();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
list.add(i);
System.out.println("Producer "+ Thread.currentThread() +"added "+i+" to the List");
con.signalAll();
lock.unlock();
}
}
}
}
class Consumer implements Runnable{
Queue<Integer> list;
Condition con;
ReentrantLock lock;
int size;
Consumer(Queue q1, Condition con, ReentrantLock l1,int size)
{
this.list=q1;
this.con=con;
this.lock=l1;
this.size=size;
}
public void run()
{
for(int innerLoop =0;innerLoop<20;innerLoop++){
if(lock.tryLock()){
while(list.size()<1){
try {
con.await();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
int i = (int) list.remove();
System.out.println("Consumer "+ Thread.currentThread() +"removed "+i+" from the List");
con.signalAll();
lock.unlock();
}
}
}
}
class SharedResource {
Queue list ;
Condition con;
ReentrantLock lock;
int size;
SharedResource()
{
size =20;
this.list=new LinkedList<Integer>();
lock = new ReentrantLock();
this.con = lock.newCondition();
}
public Queue getList() {
return list;
}
public void setList(Queue list) {
this.list = list;
}
public Condition getCon() {
return con;
}
public void setCon(Condition con) {
this.con = con;
}
public ReentrantLock getLock() {
return lock;
}
public void setLock(ReentrantLock lock) {
this.lock = lock;
}
public int getSize() {
return size;
}
public void setSize(int size) {
this.size = size;
}
}
public class MYPRODUCERCONSUMER {
public static void main(String[] args) {
SharedResource producerCObj = new SharedResource();
Producer producer= new Producer(producerCObj.getList(), producerCObj.getCon(), producerCObj.getLock(), producerCObj.getSize());
Thread producerThread= new Thread(producer);
producerThread.start();
Consumer consumer= new Consumer(producerCObj.getList(), producerCObj.getCon(), producerCObj.getLock(), producerCObj.getSize());
Thread consumerThread= new Thread(consumer);
consumerThread.start();
}
}
Начните с осознания, что здесь нет смысла делать блокировку. ArrayBlockingQueue является потокобезопасным и блокирует потоки, когда им нечего делать. Вы можете удалить все вещи с помощью замков и условий. –
@Nathan Hughes Я хочу понять, как работать с блокировкой и условиями, поэтому я изменил ArrayBlockingQueue на LinkedList. – crazyStart