兩個程序共享乙個緩衝區,乙個程序向緩衝區中寫入資料(生產者),另乙個程序從緩衝區中讀取資料(消費者)。當緩衝區被寫滿時,生產者就必須進入掛起狀態,直到消費者從緩衝區中取走資料時,生產者才能繼續向緩衝區中放資料。同樣當緩衝區沒有資料時,消費者程序就必須進入掛起狀態,直到生產者向緩衝區中放入資料時,消費者才能被喚醒繼續從緩衝區中取走資料。先實現乙個佇列:
public class arrayqueue
array[rear++] = val;
if(rear == array.length)
size++;
}public int take()
int val = array[front];
front = (front+1)%array.length;
size--;
return val;
}public int getsize()
1.建立生產者、消費者類並整合執行緒,通過thread的構造方法命名兩個執行緒;
2.通過printwriter將生產的元素和消費的元素寫到文字中用於比對;
3.覆寫run()方法,乙個呼叫put()進行生產,乙個呼叫take()進行消費;
private static arrayqueue queue = new arrayqueue();
private static class producer extends thread
printwriter printwriter;
catch (ioexception e)
}@override
public void run() catch (runtimeexception e)
}while (true);
}printwriter.close();
}}private static class customer extends thread
printwriter printwriter;
catch (ioexception e)
}@override
public void run() catch (runtimeexception e)
}while (true);
}printwriter.close();
}}public static void main(string args)
單生產者、單消費者
private int array = new int[10];
private volatile int size = 0;
private int front = 0;
private int rear = 0;
public void put(int val) throws interruptedexception
}array[rear++] = val;
if(rear == array.length)
synchronized (this)
}public int take() throws interruptedexception
}int val = array[front];
front = (front+1)%array.length;
synchronized (this)
return val;
}public int getsize()
private static arrayqueue queue = new arrayqueue();
private static class producer extends thread
@override
public void run() catch (interruptedexception e) }}
}private static class customer extends thread
@override
public void run() catch (interruptedexception e) }}
}public static void main(string args) throws interruptedexception
1、用volatile保證size變數的有序性從而保證執行緒安全;
2、size==0 或 size==array.length 時呼叫wait()方法,使執行緒進入等待集;
3、當size++或size--時通過synchronize鎖住當前引用,並且呼叫notify()喚醒生產者或消費者,保證執行緒安全;
注意:多消費者或多生產者時執行緒安全沒法保證!
private int array = new int[10];
private volatile int size = 0;
private int front = 0;
private int rear = 0;
//在take()和put()方法上加synchronize,效率低
public synchronized void put(int val) throws interruptedexception
array[rear++] = val;
if(rear == array.length)
synchronized (this)
}public synchronized int take() throws interruptedexception
int val = array[front];
front = (front+1)%array.length;
synchronized (this)
return val;
}public int getsize()
private static arrayqueue queue = new arrayqueue();
private static class producer extends thread
@override
public void run() catch (interruptedexception e) }}
}private static class customer extends thread
@override
public void run() catch (interruptedexception e) }}
}public static void main(string args) throws interruptedexception
while (producer.isalive())
}
1、當消費者和生產者執行緒都進入等待集,喚醒是隨機的,因此使用notifyall()喚醒全部執行緒,while()的作用也在此;
2、synchronize是為了防止在while語句判斷完後立馬被搶走cpu,從而導致執行緒不安全;
生產者消費者模型
1.生產者消費者問題 producer consumer 有限緩衝,多執行緒同步。生產者執行緒和消費者執行緒共享固定大小緩衝區。2.關鍵是保證生產者不會再緩衝區滿時加入資料,消費者不會在緩衝區空時消耗資料。3.解決辦法 讓生產者在緩衝區滿時休眠,等下次消費者消耗緩衝區中的資料的時候,生產者才能被喚醒...
生產者消費者模型
生產者與消費者 3,2,1 三種關係 生產者與消費者 互斥,同步 消費者與消費者 互斥 生產者與生產者 互斥 條件變數 int pthread cond destroy pthread cond t cond int pthread cond init pthread cond t restrict...
生產者消費者模型
當佇列滿時,生產者需要等待佇列有空間才能繼續往裡面放入商品,而在等待的期間內,生產者必須釋放對臨界資源 即佇列 的占用權。因為生產者如果不釋放對臨界資源的占用權,那麼消費者就無法消費佇列中的商品,就不會讓佇列有空間,那麼生產者就會一直無限等待下去。因此,一般情況下,當佇列滿時,會讓生產者交出對臨界資...