UniTO/anno2/YearI/MCAD/lesson13-15112017.md
Francesco Mecca 637cc132e2 domani mcad
2019-01-23 11:38:27 +01:00

2.5 KiB

Il bar dello stadio

Analisi di alcune soluzioni proposte del problema "il bar dello stadio".

Soluzione Semafori

semaphore mutex = 1;
semaphore pulizia = 0;
semaphore casa = 0;
semaphore ospiti = 0;
bool pulizia = false;
int n_casa = 0;
int n_ospiti = 0;
int attesa_casa = 0
int attesa_ospiti = 0;
void entra_bar_casa () {
	P (mutex);
	if (pulizia || n_casa > NMAX || n_ospiti > 0 || attesa_ospiti > 0) {
		attesa_casa++;
		V (mutex);
		P (casa);
		attesa_casa--;
	}
	n_casa++;
	if (n_casa < NMAX && attesa_casa > 0 ) {
		V(casa);
	} else {
		V(mutex);
	}
}
void esci_bar_casa () {
	P (mutex);
	n_casa--;
	if (pulizia && n_casa == 0 ) {
		V (pul);
	} else if (attesa_ospiti > 0 && !pulizia && n_casa == 0) {
		V (ospiti);
	} else if (attesa_ospiti == 0 && !pulizia && attesa_casa > 0) {
		V (casa);
	} else {
		V (mutex);
	}
}
void entra_bar_ospiti() {
	P (mutex);
	if (pulizia || n_ospiti > NMAX ) {
		attesa_ospiti++;
		V (mutex);
		P (ospiti);
		attesa_ospiti--;
	}
	n_ospiti++;
	if (n_ospiti < NMAX && attesa_ospiti > 0 ) {
		V(ospiti);
	} else {
		V(mutex);
	}
}
void esci_bar_ospiti () {
	P (mutex);
	n_ospiti--;
	if (pulizia && n_ospiti == 0 ) {
		V (pul);
	} else if (attesa_ospiti > 0 ) {
		V (ospiti);
	} else if (attesa_ospiti == 0 && !pulizia && attesa_casa > 0 && n_ospiti == 0) {
		V (casa);
	} else {
		V (mutex);
	}
}
void inizio_pulizia () {
	P (mutex);
	pulizia = true;
	if (n_ospiti > 0 || n_casa > 0) {
		V (mutex);
		P (pulizia);
	}
	V (mutex);
}
void fine_pulizia () {
	P (mutex);
	pulizia = false;
	if (attesa_ospiti > 0) {
		V (ospiti);
	} else if (attesa_casa > 0) {
		V (casa);
	} else {
		V (mutex);
	}
}

(la soluzione potrebbe non essere la migliore, implementare di nuovo)

Soluzione Monitor

(parziale, va implementata completamente)

public void apriBar () {
	chiusura = false;
	if (!empty(attesa_ospiti)) {
		signal(attesa_ospiti);
	} else if (!empty(attesa_casa)) {
		signal(attesa_casa);
	}
}
public void entra_ospite () {
	if (chiusura || n_ospiti == NMAX || n_casa > 0 ) {
		wait(attesa_ospiti);
	}
	n_ospiti++;
	if (n_ospiti < NMAX && !empty(attesa_ospiti)) {
		signal (attesa_ospiti);
	}
}
public void esci_ospite () {
	n_ospiti--;
	if (chiusura && n_ospiti == 0) {
		signal(pulizia);
	} else if (n_ospiti == 0 && empty(attesa_ospiti) && !empty(attesa_casa)) {
		signal(attesa_casa);
	} else {
		signal(attesa_ospiti);
	}
}

Soluzione con scambio di messaggi

(implementare)