java多线程 生产者消费者_java多线程之生产者消费者经典问题 - 很不错的范例
/**生產者消費者問題,涉及到幾個類
*?第一,這個問題本身就是一個類,即主類
*?第二,既然是生產者、消費者,那么生產者類和消費者類就是必須的
*?第三,生產什么,消費什么,所以物品類是必須的,這里是饅頭類
*?第四,既然是線程,那么就不是一對一的,也就是說不是生產一個消費一個,既然這樣,多生產的往哪里放,
*??????現實中就是筐了,在計算機中也就是數據結構,筐在數據結構中最形象的就是棧了,因此還要一個棧類
*/
packagethread;
publicclassProduceConsume?{
publicstaticvoidmain(String[]?args)?{
SyncStack?ss?=?newSyncStack();//建造一個裝饅頭的框
Producer?p?=?newProducer(ss);//新建一個生產者,使之持有框
Consume?c?=?newConsume(ss);//新建一個消費者,使之持有同一個框
Thread?tp?=?newThread(p);//新建一個生產者線程
Thread?tc?=?newThread(c);//新建一個消費者線程
tp.start();//啟動生產者線程
tc.start();//啟動消費者線程
}
}
//饅頭類
classSteamBread{
intid;//饅頭編號
SteamBread(intid){
this.id?=?id;
}
publicString?toString(){
return"steamBread:"+id;
}
}
//裝饅頭的框,棧結構
classSyncStack{
intindex?=0;
SteamBread[]?stb?=?newSteamBread[6];//構造饅頭數組,相當于饅頭筐,容量是6
//放入框中,相當于入棧
publicsynchronizedvoidpush(SteamBread?sb){
while(index==stb.length){//筐滿了,即棧滿,
try{
this.wait();//讓當前線程等待
}?catch(InterruptedException?e)?{
//?TODO?Auto-generated?catch?block
e.printStackTrace();
}
}
this.notify();//喚醒在此對象監視器上等待的單個線程,即消費者線程
stb[index]?=?sb;
this.index++;
}
//從框中拿出,相當于出棧
publicsynchronizedSteamBread?pop(){
while(index==0){//筐空了,即棧空
try{
this.wait();
}?catch(InterruptedException?e)?{
//?TODO?Auto-generated?catch?block
e.printStackTrace();
}
}
this.notify();
this.index--;//push第n個之后,this.index++,使棧頂為n+1,故return之前要減一
returnstb[index];
}
}
//生產者類,實現了Runnable接口,以便于構造生產者線程
classProducerimplementsRunnable{
SyncStack?ss?=?null;
Producer(SyncStack?ss){
this.ss?=?ss;
}
@Override
publicvoidrun()?{
//?開始生產饅頭
for(inti=0;i<20;i++){
SteamBread?stb?=?newSteamBread(i);
ss.push(stb);
System.out.println("生產了"+stb);
try{
Thread.sleep(10);//每生產一個饅頭,睡覺10毫秒
}?catch(InterruptedException?e)?{
//?TODO?Auto-generated?catch?block
e.printStackTrace();
}
}
}
}
//消費者類,實現了Runnable接口,以便于構造消費者線程
classConsumeimplementsRunnable{
SyncStack?ss?=?null;
publicConsume(SyncStack?ss)?{
super();
this.ss?=?ss;
}
@Override
publicvoidrun()?{
//?TODO?Auto-generated?method?stub
for(inti=0;i<20;i++){//開始消費饅頭
SteamBread?stb?=?ss.pop();
System.out.println("消費了"+stb);
try{
Thread.sleep(100);//每消費一個饅頭,睡覺100毫秒。即生產多個,消費一個
}?catch(InterruptedException?e)?{
//?TODO?Auto-generated?catch?block
e.printStackTrace();
}
}
}
}
運行結果:
總結
以上是生活随笔為你收集整理的java多线程 生产者消费者_java多线程之生产者消费者经典问题 - 很不错的范例的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 不是单组分组函数「建议收藏」
- 下一篇: java readline最后一行_ja