A barbearia na "vida" computacional possui um barbeiro dorminhoco, uma cadeira para o barbeiro cortar o cabelo do cliente e algumas cadeiras de espera. Se um cliente adentra a barbearia e o barbeiro está dormindo, ele é acordado e o cliente, atendido. Caso contrário o cliente senta em uma das cadeiras de espera. Se não há cadeiras de espera livres, o cliente simplesmente vai embora. Quando o barbeiro termina o corte de um cliente, dá uma olhada nas cadeiras de espera, se houver clientes, ele escolhe um e o atende. Caso contrário, volta a dormir até aparecerem novos clientes.
Para garantir que clientes não furem fila, que o barbeiro não durma para sempre, que os clientes em espera sejam atendidos e apenas um por vez são usados semáforos.
O código a seguir implementa a barbearia da vida computacional.
#include <pthread.h>
#include <semaphore.h>
#include <stdio.h>
#define CHAIRS 5
#define TRUE 1
#define FALSE 0
#define T_BARB 3
#define T_CUST 1
sem_t customers;
sem_t barbers;
sem_t mutex;
int waiting = 0;
void *barbeiro_thread(void *arg);
void *cliente_thread(void *arg);
void barber_sleeping(){
printf("Barbeiro dormindo...\n");
}
void cut_hair(){
printf("Barbeiro ocupado...\n");
}
void customers_waiting(int i){
printf("Clientes aguardando: %i\n",i);
}
void customer_leaves(){
printf("Cliente vai embora...\n");
}
void get_haircut(){
printf("Cliente tem o cabelo aparado...\n");
}
void barber(void){
while (TRUE) {
barber_sleeping();
sem_wait(&customers);
sem_wait(&mutex);
waiting = waiting - 1;
sem_post(&barbers);
sem_post(&mutex);
cut_hair();
sleep(T_BARB);
}
}
void customer(void){
sem_wait(&mutex);
if (waiting < CHAIRS) {
waiting = waiting + 1;
sem_post(&customers);
sem_post(&mutex);
customers_waiting(waiting);
sem_wait(&barbers);
get_haircut();
} else {
customer_leaves();
sem_post(&mutex);
}
}
void *barbeiro_thread(void *arg){
barber();
}
void *ccliente_thread(void *arg){
customer();
}
void *cliente_thread(void *arg){
pthread_t cc_thread;
while(1){
sleep(T_CUST);
pthread_create(&cc_thread,NULL,ccliente_thread,NULL);
}
}
int main(){
pthread_t b_thread;
pthread_t c_thread;
sem_init(&customers,0,0);
sem_init(&barbers,0,0);
sem_init(&mutex,0,1);
pthread_create(&b_thread,NULL,barbeiro_thread,NULL);
pthread_create(&c_thread,NULL,cliente_thread,NULL);
pthread_join(b_thread,NULL);
pthread_join(c_thread,NULL);
return 0;
}
O semáforo barbers serve para sinalizar se o barbeiro está ou não ocupado e garante que os clientes não furem fila. O semáforo customers serve para sinalizar se há clientes. O semáforo mutex garante o atendimento de apenas um cliente por vez e que todos em espera serão atendidos. O barbeiro e os clientes são threads.
Façamos a simulação de um barbeiro preguiçoso, que demora para atender os clientes, sendo que os clientes estão chegando rapidamente à barbearia. Temos o seguinte resultado:
Percebe-se que as cadeiras de espera enchem rapidamente e vários clientes vão embora.
Agora, façamos a simulação de um barbeiro eficiente, que atende rapidamente os clientes. Temos o seguinte resultado:
Percebe-se que há, no máximo, um cliente na cadeira de espera.
Páginas
Assinar:
Postar comentários (Atom)
Nenhum comentário:
Postar um comentário