Um zu verstehen, wie Multi Threading funktioniert, verwende ich Queue und ReentrantLock, um Producer und Consumer Problem zu simulieren. Mein Producer-Thread fügt Daten in die Warteschlange ein, aber Consumer entfernt nicht. Ich bin mir nicht sicher, ob ich es richtig umgesetzt habe. Ich verstehe, dass dies bereits gestellt wurde, aber sie helfen nicht.Producer Consumer mit ReentrantLock und Queue
Paket Nebenläufigkeit;
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();
}
}
Beginnen Sie mit der Erkenntnis, dass es keinen Sinn macht, hier zu sperren. ArrayBlockingQueue ist threadsicher und lässt Threads blockieren, wenn nichts für sie da ist. Sie können alle Sachen mit Sperren und Bedingungen löschen. –
@Nathan Hughes Ich möchte verstehen, wie man mit Sperre und Bedingungen arbeiten, so dass ich ArrayBlockingQueue zu LinkedList geändert habe. – crazyStart