1 生产者消费者类问题
#define semaphore int
//这里的P与V操作是按照我自己理解写的,可能会有错误
void P(semaphore p){
while(true){
if(p>0){
p-=1;
return;
}else{
wait();
}
}
}
void V(semaphore v){
v+=1;
}
//进程同步问题
//以后就把acwing 当成笔记本了
/*
1 生产者消费者问题 有一个初始为空,大小为n的缓冲区,只有缓冲区没满时,生产者才能把消息放入缓冲区,否则必须等待。只
有当缓冲区不空时,消费者才能将去除信息,否则必须等待。由于缓冲区是临界资源,所以只许可一个生产者放入消息,或者一个
消费者拿出消息。
*/
semaphore mutex=1;
semaphore empty=N;
semaphore full=0;
//按照王道操作系统上的描述
void producer(){//生产者进程的描述
while(true){
produce an item in nextp;//生产一个信息
P(empty);
P(mutex);
add nextp to buffer;
V(mutex);
V(full);
}
}
void consumer(){//消费者进程的描述
while(true){
P(full);
P(mutex);
remove an item form buffer;
V(mutex);
V(empty);
consume the item;
}
}
/*
较为复杂的生产者消费者问题,桌子上有一个个水果盘,每次之能放入一个水果,爸爸想盘子中放苹果,妈妈像盘子中放橘子,儿子只
吃橘子,女儿只吃苹果。只有当盘子中为空时才能放入水果,只有盘子中不为空时儿子或女儿才吃水果。
*/
semaphore plate=1, apple=0, orange=0;
void dad(){
while(true){
prepare an apple;
P(plate);
put an apple on the plate;
V(apple);
}
}
void mom(){
while(true){
prepare an orange;
P(plate);
put an orange on the plate;
V(orange);
}
}
void son(){
while(true){
P(orange);
get an orange from plate;
V(plate);
eat the orange;
}
}
void daughter(){
while(true){
P(apple);
get an apple from plate;
V(plate);
eat the apple;
}
}
2 读者写者问题
/*
2 读者,写者问题 有读者和写者两个进程,共享一个文件,当两个或以上的读者访问时不会出问题,但是某个写进程和其他进程(
包括读或者其他写进程)同时访问数据时可能会出现错误。因此要求1 允许多个都进程同时对文件执行读操作2 只允许一个写进程
对文件进行写操作。3任何一个写进程在完成写进程以前不允许其他进程的写操作或者读操作4 写者进行写操作前,所有的读者都
退出
*/
//方法1,这个写法是读者优先的,只要文件中有读者,就会一直阻碍写进程,这样写进程有可能会被饿死哦 (/≧▽≦)/
int count=0;
semaphore mutex=1;
semaphore rw=1;
void writer(){
while(true){
P(rw);
write;
V(rw);
}
}
void reader(){
while(true){
P(mutex);
if(count==0){
P(rw);//阻止写进程
}
count+=1;
V(mutex);
read;
P(mutex);
count-=1;
if(count==0){
V(rw);
}
count-=1;
V(mutex);
}
}
// 方法二,为了保证写进程不会被饿死,一旦写进程要准备写操作时,就阻挡后续的所有读进程
int count=0;
semaphore mutex=1;
semaphore rw=1;
semaphore w=1;
void writer(){
while(true){
P(w);
P(rw);
write;
V(rw);
V(w);
}
}
void reader(){
while(true){
P(w);//只有无写入进程时才能进入
P(mutex);
if(count==0){
P(rw);
}
count+=1;
V(mutex);
V(w);
read;
P(mutex);
count-=1;
if(count==0){
V(rw);
}
V(mutex);
}
}
3 哲♂学家用餐问题
/*
3 哲♂学家进餐问题,一个圆桌上有5个哲♂学家,每两个哲♂学家之间有一支筷子,哲♂学家正对着一碗米饭
哲♂学家只有思考或者进餐,进餐时需要拿起其两边的筷子,进餐完毕后便放下筷子
*/
/*方法1:为了防止哲♂学家因为争夺筷子造成死锁导致摔♂跤,采用这种策略:编号为基数的哲♂学家优先使用左手
边的筷子,而编号为偶数的哲♂学家优先使用右手边的筷子
*/
semaphore chopstick[5]={1,1,1,1,1};
void Pi(){
while(true){
if(id%2==0){
P(chopstick[i]);
P(chopstick[(i+1)%5]);
}else{
P(chopstick[(i+1)%5]);
P(chopstick[i]);
}
eat;
if(id%2==0){
V(chopstick[i]);
V(chopstick[(i+1)%5]);
}else{
V(chopstick[(i+1)%5]);
V(chopstick[i]);
}
think;
}
}
/*
方法2: 同一时刻只允许一个哲♂学家争取筷子,且只有当其两边筷子都存在时才用餐
*/
semaphore chopstick[5]={1,1,1,1,1};
semaphore mutex=1;
void Pi(){
while(true){
P(mutex);
P(chopstick[i]);
P(chopstick[(i+1)%5]);
V(mutex);
eat;
P(chopstick[i]);
P(chopstick[(i+1)%5]);
think;
}
}
/*
这是按照王道考研上的方法写的,但是感觉存在一些小问题,比如现在只有1号哲学♂家在用餐,这时2号哲♂学家
也要开始用餐,但是他要等待1号哲♂学家,此时2号哲♂学家锁定mutex信号。假设此时4号哲♂学家也要用餐,但是
他要等待2号释放mutex信号才行。但实际上2号哲♂学家与4号哲♂学家毫无关联。
*/
4 吸烟者问题
/*
4 吸烟者问题,现在有三个吸烟者和一个供应者,每个吸烟者都在不停的卷烟并且抽烟,但是卷烟需要三种材料,
分别是烟草,纸和胶水,其中,第一个吸烟者有胶水,第二个吸烟者有烟草,第三个吸烟者有纸,供应者有无限
的三种材料,但是每次只会选择两种放在桌子上,用有剩下材料的吸烟者用它们来来卷一支烟并且吸掉它。
*/
int random;
semaphore offer1=0;//提供烟草和纸的信号
semaphore offer2=0;//提供烟草和胶水的信号
semaphore offer3=0;//提供胶水和纸的信号
semaphore finish=0;
void Offer(){
while(true){
random=随意一个随机数;
random%=3;
if(random==0){
V(offer1);
}else if(random==1){
V(offer2);
}else{
V(offer3);
}
提供对应的材料;
P(finish);
}
}
void p1(){
while(true){
P(offer1);
使用对应缺少的材料;
V(finish);
}
}
void p2(){
while(true){
P(offer2);
使用对应缺少的材料;
V(finish);
}
}
void p3(){
while(true){
P(offer3);
使用对应缺少的材料;
V(finish);
}
}
里面可能有错的( ´•︵•` )......