題目
有一個倉庫存放兩種零件A和B,最大庫存容量各為m個,有一車間不斷取A和B進行裝配,每次各取一個。為避免零件銹蝕,遵循先入庫先出庫原則,有兩個供應商分別不斷地供應A和B 。為保證齊套和合理庫存,當某種零件的數量比另一種的數量超過n(n<m)個時,暫停對數量大的零件進貨,集中補充數量少的零件。試用P、V操作正確實現之。
關鍵句子
- 最大庫存容量各為m個;
- 一車間不斷取A和B進行裝配,每次各取一個;
- 兩個供應商分別不斷地供應A和B (兩供應商之間的互斥);
- 當某種零件的數量比另一種的數量超過n(n<m)個時,暫停對數量大的零件進貨,集中補充數量少的零件 (兩供應商之間的同步);
同步和互斥(根據這個設信號量)
- 兩個供應商和車間操作倉庫的 互斥;
- 兩個供應商之間的變形 同步(數量相差n);
- 兩個供應商和車間的 同步(有容量入庫,有庫存出庫);
思路
- 首先明確兩個供應商和車間操作倉庫是互斥的,所以三個進程的代碼中間都是搶奪這個權限的;
int mutex = 1; //操作倉庫的權限
PinA(){
P(mutex);
//入庫A零件
V(mutex);
}
PinB(){
P(mutex);
//入庫B零件
V(mutex);
}
Pout(){
P(mutex);
//出庫A和B零件
V(mutex);
}
- 然后先解決車間出庫的進程問題。在出庫之前,必須要有零件A和零件B;
int countA = m; //A的庫存
int countB = m; //B的庫存
int mutex = 1; //操作倉庫的權限
PinA(){
P(mutex);
//入庫A零件
V(mutex);
}
PinB(){
P(mutex);
//入庫B零件
V(mutex);
}
Pout(){
//這段代碼不完善,PV操作的數量要相同,這里只是跟着思路寫一下
P(countA);
P(countB);
P(mutex);
//出庫A和B零件
V(mutex);
}
- 因為入庫出庫之間有一個同步的關系,必須要有位置才能入庫,必須要有庫存才能出庫,所以要用兩個變量實現這個同步,一個count不足以解決這個問題;
int emptyA = m; //A的剩余庫存容量
int emptyB = m; //B的剩余庫存容量
int fullA = 0; //A的庫存數量
int fullB = 0; //B的庫存數量
int mutex = 1; //操作倉庫的權限
PinA(){
P(emptyA);
P(mutex);
//入庫A零件;
V(mutex);
V(fullA);
}
PinB(){
P(emptyB);
P(mutex);
//入庫A零件;
V(mutex);
V(fullB);
}
Pout(){
P(fullA);
P(fullB);
P(mutex);
//出庫A和B零件
V(mutex);
V(emptyB);
V(emptyA);
}
- 最后要解決的就是當某種零件的數量比另一種的數量超過n(n<m)個時,暫停對數量大的零件進貨,集中補充數量少的零件這個問題。這里我是上網找資料才知道怎么解決的。這是兩供應商之間的一種同步,一種變形的同步
解釋(看完代碼再看):舉個最簡單的例子,假如一開始一直都是入庫A零件,當入庫了n個時,B零件和A零件的數量就相差了n個了,那么Sa=0,供應商A不能參與爭奪操作倉庫的權限了。
int emptyA = m; //A的剩余庫存容量
int emptyB = m; //B的剩余庫存容量
int fullA = 0; //A的庫存數量
int fullB = 0; //B的庫存數量
int Sa = n; //A和B的相差數量
int Sb = n; //Sa和Sb實現AB入庫的同步
int mutex = 1; //操作倉庫的權限
PinA(){
P(emptyA);
P(Sa);
P(mutex);
//入庫A零件;
V(mutex);
V(Sb);
V(fullA);
}
PinB(){
P(emptyB);
P(Sb);
P(mutex);
//入庫A零件;
V(mutex);
V(Sa);
V(fullB);
}
Pout(){
P(fullA);
P(fullB);
P(mutex);
//出庫A和B零件
V(mutex);
V(emptyB);
V(emptyA);
}
完整代碼
int emptyA = m; //A的剩余庫存容量
int emptyB = m; //B的剩余庫存容量
int fullA = 0; //A的庫存數量
int fullB = 0; //B的庫存數量
int Sa = n; //A和B的相差數量
int Sb = n; //Sa和Sb實現AB入庫的同步
int mutex = 1; //操作倉庫的權限
main(){
PinA();
PinB();
Pout();
}
PinA(){
P(emptyA);
P(Sa);
P(mutex);
//入庫A零件;
V(mutex);
V(Sb);
V(fullA);
}
PinB(){
P(emptyB);
P(Sb);
P(mutex);
//入庫A零件;
V(mutex);
V(Sa);
V(fullB);
}
Pout(){
P(fullA);
P(fullB);
P(mutex);
//出庫A和B零件
V(mutex);
V(emptyB);
V(emptyA);
}
總結
- 老師是說做這種題目要先想好信號量和變量,不過我按照老師說的方法的確做不出來,還是要想好幾個大概的信號量,再邊寫邊改。