使用wait()與notifyAll()實現生產者與消費者模式
使用wait()與notifyAll()實現生產者與消費者模式
所涉及到的基礎知識
wait()
一、wait是java同步機制中重要的組成部分。結合與synchronized關鍵字使用,否則執行時會收到一個異常:IllegalMonitorStateException。
二、wait屬於Object類。
三、呼叫任意物件的 wait() 方法導致該執行緒阻塞,並且會釋放鎖。
notify()、notifyAll()
一、notify、notifyAll是java同步機制中重要的組成部分。結合與synchronized關鍵字使用。
二、notify、notifyAll屬於Object類。
三、notify與notifyAll沒有太多的區別,只是notify僅喚醒一個執行緒並允許它去獲得鎖,notifyAll是喚醒所有等待這個物件的執行緒並允許它們去獲得物件鎖,只要是在synchronied塊中的程式碼,沒有物件鎖是寸步難行的。其實喚醒一個執行緒就是重新允許這個執行緒去獲得物件鎖並向下執行。
程式碼示例
生產者:
import java.util.List;
import java.util.Random;
public class Productor implements Runnable {
private final int CAPACITY_SIZE = 5;//容器可容納最大數
private final List<String> container;
public Productor(List<String> container){this.container = container;}
@Override
public void run() {
while (true){
product();
}
}
Random random = new Random();
private void product(){
try {
synchronized (container){
while (container.size() == CAPACITY_SIZE){
System.out.println("容器已經滿了,等待消費者消費");
container.wait();
}
String productor = getRandomString(5);
container.add(productor);
System.out.println("生產出產品:"+productor);
Thread.sleep(1000);
container.notifyAll();
}
}catch (Exception e){
e.printStackTrace();
}
}
//length使用者產生字串的長度
private static String getRandomString(int length){
String str="abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
Random random=new Random();
StringBuffer sb=new StringBuffer();
for(int i=0;i<length;i++){
int number=random.nextInt(62);
sb.append(str.charAt(number));
}
return sb.toString();
}
}
消費者:
import java.util.List;
public class Consumer implements Runnable {
private final List<String> container;
public Consumer(List<String> container){this.container = container;}
@Override
public void run() {
while (true){
consum();
}
}
private void consum() {
try {
synchronized (container){
while (container.isEmpty()){
System.out.println("已消費完");
container.wait();
}
System.out.println("消費產品:"+container.get(0));
container.remove(0);
Thread.sleep(2000);
container.notifyAll();
}
}catch (Exception e){
e.printStackTrace();
}
}
}
測試程式碼:
import java.util.ArrayList;
import java.util.List;
public class TestProductorAndConsumer
{
public static void main(String[] args) {
List<String> con = new ArrayList<>();
Productor productor = new Productor(con);
Consumer consumer = new Consumer(con);
new Thread(productor).start();
new Thread(consumer).start();
}
}
執行結果:
相關文章
- java進階(40)--wait與notify(生產者與消費者模式)JavaAI模式
- 九、生產者與消費者模式模式
- 使用BlockQueue實現生產者和消費者模式BloC模式
- 「Kafka應用」PHP實現生產者與消費者KafkaPHP
- 生產者消費者模式模式
- 生產者與消費者問題
- 生產消費者模式模式
- python 多執行緒實現生產者與消費者模型Python執行緒模型
- python 生產者消費者模式Python模式
- 使用Disruptor實現生產者和消費者模型模型
- python執行緒通訊與生產者消費者模式Python執行緒模式
- 生產者與消費者之Android audioAndroid
- linux 生產者與消費者問題Linux
- Java中的設計模式(二):生產者-消費者模式與觀察者模式Java設計模式
- Java實現生產者和消費者Java
- 生產者消費者模式,以及基於BlockingQueue的快速實現模式BloC
- java實現生產者消費者問題Java
- 執行緒間的協作(2)——生產者與消費者模式執行緒模式
- 併發設計模式---生產者/消費者模式設計模式
- 讀者寫者與生產者消費者應用場景
- 生產者消費者
- 阻塞佇列和生產者-消費者模式佇列模式
- PHP操作Beanstalkd佇列(2)生產者與消費者PHPBean佇列
- 生產者消費者模型模型
- java編寫生產者/消費者模式的程式。Java模式
- Python-多執行緒及生產者與消費者Python執行緒
- 使用Python佇列和多執行緒實現生產者消費者Python佇列執行緒
- C++ condition_variable 實現生產者消費者模型C++模型
- 生產者消費者問題-C++程式碼實現C++
- Java 多執行緒基礎(十二)生產者與消費者Java執行緒
- Java多執行緒——消費者與生產者的關係Java執行緒
- 使用ZIO-Streams的Redis Stream消費者和生產者實現原始碼Redis原始碼
- 面試必問:訊號量與生產者消費者問題!面試
- ActiveMQ 生產者和消費者demoMQ
- 多執行緒併發如何高效實現生產者/消費者?執行緒
- 新手練習-消費者生產者模型模型
- 使用pthread_mutex_t與條件變數pthread_cond_t的組合來實現生產者和消費者threadMutex變數
- 多生產者-消費者中假死現象的處理