第一关:生产者与消费者问题
信号量是4个,除了题目里已经给出的2个之外,还有分别针对生产者和消费者的mutex。
切记要把四个信号量在同一行中定义!
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <unistd.h>
#include <pthread.h>
#include <semaphore.h>
#define N 8
#define PRODUCT_NUM 15
int buffer[N], readpos = 0, writepos = 0;
sem_t full, empty, mutexC, mutexP; //添加生产者和消费者的mutex
void sleep_random(int t) {
sleep((int)(t * (rand() / (RAND_MAX *1.0))));
}
#define PRODUCER_CNT 5
#define CONSUMER_CNT 5
void *produce(void *idx){
int id =*((int*)idx); //创建线程的id
int i;
for (i = 0; i < PRODUCT_NUM; i++){
sleep_random(2);
sem_wait(&empty);
sem_wait(&mutexP);
sem_wait(&mutexC);
buffer[writepos++] = 1000*(id) + i + 1;
if (writepos >= N)
writepos = 0;
printf("produce: %d\n", 1000*(id) + i + 1);
sem_post(&mutexC);
sem_post(&mutexP);
sem_post(&full);
}
}
void *consume(){
int i;
for (i = 0; i < PRODUCT_NUM; i++){
sleep_random(2);
sem_wait(&full);
sem_wait(&mutexP);
printf("consume: %d\n", buffer[readpos]);
buffer[readpos++] = - 1;
if (readpos >= N)
readpos = 0;
sem_post(&mutexP);
sem_post(&empty);
}
}
int main(){
int res, i;
pthread_t t1[PRODUCER_CNT],t2[CONSUMER_CNT];
for (i = 0; i < N; i++)
buffer[i] = - 1;
srand((int)time(0));
sem_init(&full, 0, 0);
sem_init(&empty, 0, N);
sem_init(&mutexP, 0, 1);
sem_init(&mutexC, 0, 1);
for (i = 0; i < PRODUCER_CNT; i++)
res = pthread_create(&t1[i], NULL, produce, &i);
if (res != 0){
perror("failed to create thread");
exit(1);
}
for (i = 0; i < CONSUMER_CNT; i++)
res = pthread_create(&t2[i], NULL, consume, NULL);
if (res != 0){
perror("failed to create thread");
exit(1);
}
void* resj;
for(i = 0; i < PRODUCER_CNT; i++){
pthread_join(t1[i],&resj);
}
for(i = 0; i < CONSUMER_CNT; i++){
pthread_join(t2[i],&resj);
}
return 0;
}
第二关:三个并发进程
不要看到长空格就写\t,要换成8个空格才能通过(以下代码使用了\t)
注意几个信号量的请求顺序
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <unistd.h>
#include <pthread.h>
#include <semaphore.h>
#define LIMIT 20
#define M 5
#define N 8
/************************************/
sem_t mtp,mtq,mtr,full1,empty1,empty2,full2;
int buffer1[M],buffer2[N];
/************************************/
void sleep_random(int t) {
sleep((int)(t * (rand() / (RAND_MAX *1.0))));
}
void *P(){
int i;
for (i = 0; i < LIMIT; i++){
sleep_random(2);
/************************************/
sem_wait(&empty1);
sem_wait(&mtq);
sem_wait(&mtp);
buffer1[i%M]=i+1;
printf("P sends:\t%d\n",i+1);
sem_post(&mtp);
sem_post(&mtq);
sem_post(&full1);
/************************************/
}
}
void *Q(){
int i, data;
for (i = 0; i < LIMIT; i++){
sleep_random(2);
/************************************/
int t;
sem_wait(&full1);
sem_wait(&mtp);
sem_wait(&mtq);
t=buffer1[i%M];
sem_post(&mtq);
sem_post(&mtp);
sem_post(&empty1);
sem_wait(&empty2);
sem_wait(&mtr);
sem_wait(&mtq);
buffer2[i%N]=t;
sem_post(&mtq);
sem_post(&mtr);
sem_post(&full2);
/************************************/
}
}
void *R(){
int i;
for (i = 0; i < LIMIT; i++){
sleep_random(2);
/************************************/
sem_wait(&full2);
sem_wait(&mtq);
sem_wait(&mtr);
printf("R receives: %d\n",buffer2[i%N]);
sem_post(&mtr);
sem_post(&mtq);
sem_post(&empty2);
/************************************/
}
}
int main(){
int i;
pthread_t t1, t2;
for (i = 0; i < M; i++)
buffer1[i] = - 1;
for (i = 0; i < N; i++)
buffer2[i] = - 1;
srand((int)time(0));
/************************************/
sem_init(&mtp,0,1);
sem_init(&mtq,0,1);
sem_init(&mtr,0,1);
sem_init(&full1,0,0);
sem_init(&empty1,0,M);
sem_init(&full2,0,0);
sem_init(&empty2,0,N);
/************************************/
pthread_create(&t1, NULL, P, NULL);
pthread_create(&t2, NULL, Q, NULL);
R();
return 0;
}
第三关:理发师问题
可以理解为缓存容量分别为2,1,1的第二题。信号量的排序需要注意。
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <unistd.h>
#include <pthread.h>
#include <semaphore.h>
#define SEAT_NUM 2
#define CUSTOMER_NUM 5
/************************************/
sem_t empty,full,empty2,full2,mtb,mtw;//mutex lock for the barber and waiting room
int buffer[SEAT_NUM], cur_serv, readpos = 0, writepos = 0;//waiting room
/************************************/
void sleep_random(int t) {
sleep((int)(t * (rand() / (RAND_MAX *1.0))));
}
void *barber()
{
while(5)
{
/************************************/
sem_wait(&full);
buffer[readpos++] = -1;
if (readpos >= SEAT_NUM){
readpos = 0;
}
sem_post(&empty);
sem_wait(&empty2);
/************************************/
printf("barber: start cutting\n");
sleep_random(3);
printf("barber: finish cutting\n");
/************************************/
sem_post(&full2);
/************************************/
}
}
void *customer(void *id)
{
const int myid = *(int*)id;
sleep_random(2);
printf("customer %d: enter waiting-room\n", myid);
/************************************/
sem_wait(&empty);
sem_wait(&mtw);
/************************************/
printf("customer %d: sit down\n", myid);
/************************************/
buffer[writepos++] = myid;
if (writepos >= SEAT_NUM)
writepos = 0;
sem_post(&mtw);
sem_wait(&mtb);
/************************************/
printf("customer %d: enter cutting-room and sit down\n", myid);
/************************************/
cur_serv = myid;
sem_post(&full);
sem_wait(&full2);
/************************************/
printf("customer %d: bye\n", myid);
/************************************/
sem_post(&mtb);
sem_post(&empty2);
/************************************/
}
int main()
{
int i, id[CUSTOMER_NUM];
pthread_t t[CUSTOMER_NUM];
srand((int)time(0));
/************************************/
sem_init(&empty,0,SEAT_NUM);
sem_init(&full,0,0);
sem_init(&full2,0,0);
sem_init(&empty2,0,1);
sem_init(&mtb,0,1);
sem_init(&mtw,0,1);
/************************************/
for (i = 0; i < CUSTOMER_NUM; i++)
{
id[i] = i + 1;
pthread_create(&t[i], NULL, customer, &id[i]);
}
barber();
return 0;
}
本文转载自: https://blog.csdn.net/qq_33965473/article/details/128117312
版权归原作者 tzzzzzzzx 所有, 如有侵权,请联系我们删除。
版权归原作者 tzzzzzzzx 所有, 如有侵权,请联系我们删除。