Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #!/bin/python
- # -*- coding: utf-8 -*-
- ########################################################
- # Implémentation du problème du dîner des philosophes. #
- # Par Julien Delplanque #
- # Le 18/01/2014 #
- ########################################################
- import thread
- import time
- """
- Cette classe représente un verrou exclusif.
- """
- class Exclusif(object):
- def __init__(self):
- self.valeur = False
- def __str__(self):
- if self.valeur:
- return "locked"
- else:
- return "unlocked"
- """
- Cette classe représente un sémaphore, nécessaire pour cette implémentation en python
- car nous ne disposons pas de pointeurs.
- """
- class Semaphore(object):
- def __init__(self,v):
- self.valeur = v
- def __str__(self):
- return str(self.valeur)
- """
- Incrémente la valeur du sémaphore.
- """
- def increase(self):
- self.valeur += 1
- """
- Décrémente la valeur du sémaphore.
- """
- def decrease(self):
- self.valeur += 1
- """
- Retourne une string à partir d'une liste de Semaphore dans un format similaire à la
- représentation sous forme de string d'une liste.
- """
- @staticmethod
- def tabStr(tab):
- sTab = "["
- for i in range(len(tab)-1):
- sTab += str(tab[i])+","
- sTab += str(tab[N-1])+"]"
- return sTab
- """
- Processus philosophe.
- """
- def philosophe(i):
- while True:
- ETAT[i] = "PENSE"
- prendFourch(i)
- ETAT[i] = "MANGE"
- poseFourch(i)
- """
- Prendre les deux fourchettes.
- """
- def prendFourch(i):
- wait(MUTEX)
- ETAT[i] = "FAIM"
- test(i)
- signal(MUTEX)
- wait(S[i])
- """
- Poser les deux fouchettes.
- """
- def poseFourch(i):
- wait(MUTEX)
- ETAT[i] = "PENSE"
- test(voisinG(i))
- test(voisinD(i))
- signal(MUTEX)
- """
- Retourne l'indice du voisin de gauche du philosophe i.
- """
- def voisinG(i):
- return (i+N-1)%N
- """
- Retourne l'indice du voisin de droite du philosophe i.
- """
- def voisinD(i):
- return (i+1)%N
- """
- Tenter de saisir les deux fouchettes.
- """
- def test(i):
- if ETAT[i] == "FAIM" and ETAT[voisinG(i)] != "MANGE" and ETAT[voisinD(i)] != "MANGE":
- ETAT[i] = "MANGE"
- signal(S[i])
- """
- Permet de d'effectuer le wait et signal de manière atomique en verrouillant l'accès
- au sémaphore. Les opérations entre lock() et unlock() font donc parti de la section
- critique.
- """
- def lock(e):
- while e.valeur:
- pass
- e.valeur = True
- """
- Permet de d'effectuer le wait et signal de manière atomique en déverrouillant l'accès
- au sémaphore. Les opérations entre lock() et unlock() font donc parti de la section
- critique.
- """
- def unlock(e):
- e.valeur = False
- """
- Permet de faire un wait sur le sémaphore s.
- """
- def wait(s):
- while s.valeur <= 0:
- pass
- lock(EXCLUSIF)
- s.decrease()
- unlock(EXCLUSIF)
- """
- Permet de faire un signal sur le sémaphore s.
- """
- def signal(s):
- lock(EXCLUSIF)
- s.increase()
- unlock(EXCLUSIF)
- if __name__=="__main__":
- MUTEX = Semaphore(1) # Sémaphore d'exclusion mutuelle.
- S = [Semaphore(0),Semaphore(0),Semaphore(0),Semaphore(0),Semaphore(0)] # Liste des sémaphores.
- ETAT = ["PENSE","PENSE","PENSE","PENSE","PENSE"] # Liste des états.
- EXCLUSIF = Exclusif()
- assert len(S) == len(ETAT) # S'assurer que les tailles de S et et ETAT sont égales.
- N = len(S) # Le nombre de philosophes.
- DELAY = 0.5 # Delay entre chaque affichage.
- try:
- thread.start_new_thread( philosophe, (0, ) )
- thread.start_new_thread( philosophe, (1, ) )
- thread.start_new_thread( philosophe, (2, ) )
- thread.start_new_thread( philosophe, (3, ) )
- thread.start_new_thread( philosophe, (4, ) )
- except:
- print "Erreur, impossible de démarrer les threads."
- while True:
- print "S: "+Semaphore.tabStr(S)
- print "ETAT: "+str(ETAT)
- print "MUTEX: "+str(MUTEX)
- print "EXCLUSIF: "+str(EXCLUSIF)
- print "--------------------"
- time.sleep(DELAY)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement